Markdown Lists
Bullet, numbered, and nested lists in Markdown: the exact indentation a nested item needs, how numbering really works, and why a list breaks or restarts.
Short answer
Start each line with - for a bullet or 1. for a number. To nest an item, indent it so its marker lines up with the parent's text: 2 spaces under a bullet, 3 under a number. Only the first number counts, so 1. on every line still renders 1, 2, 3. Leave a blank line before the list and after it.
Bullet Lists
Start each line with a hyphen, asterisk, or plus sign followed by a space. All three produce the same bullets.
- First item
- Second item
- Third item- First item
- Second item
- Third item
- Hyphen item
- Hyphen item
* Asterisk item
+ Plus item- Hyphen item
- Hyphen item
- Asterisk item
- Plus item
In CommonMark and GitHub this is three separate lists, not one: changing from - to * or + ends the list. Pick one marker and stick with it.
Numbered Lists
Use a number, a period, and a space. The first number sets where the list starts. Every number after it is ignored, and the renderer counts up on its own.
1. First step
2. Second step
3. Third step- First step
- Second step
- Third step
3. Third step
4. Fourth step
5. Fifth step- Third step
- Fourth step
- Fifth step
Renders as <ol start="3">. Any number up to 9 digits works, including 0. If the list follows a paragraph, it needs a blank line above it, because only a list starting at 1 can interrupt a paragraph.
1. First step
1. Second step
1. Third step- First step
- Second step
- Third step
Still renders 1, 2, 3. Handy when you reorder steps often; explicit numbers read better in the raw file.
1) First step
2) Second step- First step
- Second step
1) works the same as 1. in CommonMark and GitHub. Mixing the two in one list starts a new list at the switch.
Nested Lists
A nested item belongs to the item above it when it is indented at least as far as that item's text. CommonMark calls this the content column: the width of the marker plus the space after it. GitHub's own docs give the same rule: line the nested marker up under the first character of the parent's text.
| Parent line | Text starts at column | Child indent that nests |
|---|---|---|
| - Parent | 2 | 2 to 5 spaces |
| 1. Parent | 3 | 3 to 6 spaces |
| 10. Parent | 4 | 4 to 7 spaces |
- Fruits
- Apple
- Banana
- Vegetables
- Carrot
- Purple carrot- Fruits
- Apple
- Banana
- Vegetables
- Carrot
- Purple carrot
- Carrot
1. Plan
1. Research
2. Design
2. Build
- Frontend
- Backend- Plan
- Research
- Design
- Build
- Frontend
- Backend
Numbered and bullet items mix freely. The child just has to clear the parent's marker.
10. Tenth step
- Indented 4 spaces to clear "10. "
11. Eleventh step- Tenth step
- Indented 4 spaces to clear "10. "
- Eleventh step
"10. " is four characters wide, so 3 spaces would not reach the text and the child would fall out of the list.
- and 1. because up to 3 spaces beyond the content column are allowed. So 4 spaces is the portable choice, and 2 is the minimum on GitHub. Go past the window, though, and the line stops being a list item: it joins the parent's text, or after a blank line it becomes a code block. See the indentation guide for tabs and the code-block rule.Task Lists
A task list is a list item that starts with [ ] or [x]. It is a GitHub Flavored Markdown extension rather than core syntax. The Markdown checkbox guide covers where the boxes are clickable, nesting, and tables.
- [x] Write documentation
- [ ] Update screenshots
- [ ] Deploy to production- Write documentation
- Update screenshots
- Deploy to production
Keep or Resume Numbering
The usual reason a numbered list restarts at 1 is that something between the items ended it. There are two fixes. The first is better when the extra content belongs to a step: indent it into the item so the list never ends.
1. Install the package:
```sh
npm install marked
```
2. Import it.
3. Call marked.parse().Install the package:
npm install markedImport it.
Call marked.parse().
The fence is indented 3 spaces, the width of 1. plus its space, so it belongs to step 1.
1. First item
2. Second item
A paragraph that ends the list.
3. Third item
4. Fourth item- First item
- Second item
A paragraph that ends the list.
- Third item
- Fourth item
When the content really sits between two lists, start the second list at the next number. The blank line before 3. is required.
Tight vs Loose Lists
A blank line between any two items makes the whole list loose: each item is wrapped in a paragraph and gets paragraph spacing. One stray blank line is enough to change every item, so remove them for a compact list.
- Milk
- Eggs
- Bread- Milk
- Eggs
- Bread
- Milk
- Eggs
- BreadMilk
Eggs
Bread
All three items now render as <li><p>…</p></li>, not just the first two.
Platform Variations
Document renderers follow the rules above. Chat and note apps convert list shortcuts as you type, and each has its own limits.
- [x] Write documentation
- [ ] Update screenshots
- [ ] Deploy to production- Write documentation
- Update screenshots
- Deploy to production
Full GFM lists, including task lists. In issues, pull requests, and comments the checkboxes are clickable; in a README or other .md file they are read-only.
* first
* second- first
- second
The message composer turns * + space into a bulleted list and 1. + space into a numbered one. Messages sent by apps as plain mrkdwn have no list syntax at all; a Block Kit markdown block renders standard - and 1. lists.
- first
- nested (2 spaces)
- second- first
- nested (2 spaces)
- second
Bullets with - or *, numbers with 1., and 2 spaces before the marker to indent a level (per Discord's own guide). Task list brackets show up as plain text.
- first
- second- first
- second
Type -, *, or + then space for a bulleted list, and 1., a., or i. then space for a numbered one. Tab nests the current item, Shift+Tab un-nests it.
Common Mistakes
Almost every broken list is an indentation or blank-line problem. Each row shows the broken version and the fix.
Broken
-First item
-Second itemFixed
- First item
- Second itemBroken
1. Parent step
- Child itemFixed
1. Parent step
- Child itemBroken
- Fruits
- Apple
- BananaFixed
- Fruits
- Apple
- BananaBroken
1. Install:
```sh
npm install
```
1. Run it.Fixed
1. Install:
```sh
npm install
```
2. Run it.Broken
Remaining steps:
3. Deploy
4. AnnounceFixed
Remaining steps:
3. Deploy
4. AnnounceBroken
- Last item
This was meant to be a new paragraph.Fixed
- Last item
This is a new paragraph.Quick Reference
| Syntax | Result | Notes |
|---|---|---|
| - item | Bullet | - * + all work; switching starts a new list |
| 1. item | Numbered | First number sets the start |
| 1) item | Numbered | CommonMark/GitHub; not old Reddit |
| 3. item | Starts at 3 | Needs a blank line above it after a paragraph |
| - item - child | Nested bullet | 2 spaces under - |
| 1. item - child | Nested under number | 3 spaces under 1. |
| 1. step more text | Second paragraph in an item | Indent to the item's text |
| - [ ] task | Unchecked task | GFM extension |
| - [x] task | Checked task | GFM extension |
Platform Support
Basic bullets and numbers work almost everywhere. Nesting depth rules, alternative markers, and task lists are where platforms differ.
| Platform | Supported? | Notes |
|---|---|---|
| CommonMark | Yes | Bullets (- * +), numbers with . or ), any start number, nesting by content column. Task lists are not core syntax. |
| GitHub / GitLab | Yes | CommonMark lists plus GFM task lists. GitHub's docs say to indent a child to the first character of the parent's text. |
| VS Code preview | Yes | CommonMark lists; task lists render as read-only checkboxes. |
| Obsidian | Yes | Any list type nests under any other. Tab and Shift+Tab indent and un-indent selected items. |
| MkDocs (Python-Markdown) | Partial | Nested items need 4 spaces per level, and a change of marker does not start a new list. Task lists need an extension. |
| Yes | Sublists need 2 spaces under a bullet and 3 under a number. 1) markers work on www.reddit.com only; use 1. for old Reddit too. | |
| Notion | Yes | Markdown shortcuts create native list blocks; Tab nests. |
| Discord | Partial | Bullets, numbers, and 2-space indented sublists. No task lists. |
| Slack | Partial | Lists in the composer and in Block Kit markdown blocks. Plain mrkdwn has no list syntax. |
Frequently Asked Questions
How do you make a list in Markdown?
Start each line with a marker and a space. A hyphen, asterisk, or plus sign (- item) makes a bulleted list. A number followed by a period (1. item) makes a numbered list.
How do you make a nested list in Markdown?
Indent the child item so its marker lines up with the first character of the parent's text. That is 2 spaces under a - item, 3 spaces under a 1. item, and 4 under a 10. item. Every line at the same level needs the same indent.
How many spaces do you need to indent a nested list?
In CommonMark and GitHub, the minimum is the width of the parent's marker plus its space: 2 under -, 3 under 1. Up to 3 extra spaces also nest, so 4 spaces works under - and 1. too. 4 spaces per level is required in Python-Markdown (MkDocs), which makes it the safest choice if your file has to render in more than one place.
Is it true that nested lists need 4 spaces?
Not in CommonMark or GitHub Flavored Markdown. The rule there is to line the child up with the parent's text, which is 2 spaces under a bullet. The 4-space rule comes from the original Markdown and Python-Markdown, which MkDocs uses. 4 spaces happens to work in both, which is why it is often given as the universal answer.
How do I start a numbered list at a number other than 1?
Start the first item at that number: 3. Third step. The renderer outputs <ol start="3"> and counts up from there. Only the first number matters, and the list needs a blank line above it if it follows a paragraph.
Do I have to number every item correctly?
No. Only the first item's number is used; the rest are ignored. Writing 1. on every line renders 1, 2, 3, which keeps diffs small when you reorder items. Explicit numbers are easier to read in the raw file.
How do I keep the numbering going after a code block or paragraph?
Indent the code block or paragraph so it belongs to the list item above it: 3 spaces under a 1. item. It then sits inside that item and the list continues. If you let it end the list instead, start the next list at the number you want, such as 3.
Can I use 1) instead of 1. for numbered lists?
Yes in CommonMark and GitHub: 1) and 1. both make an ordered list. Switching between them, or between -, *, and +, starts a new list. Some older parsers, including old Reddit, only accept the period.
Why does my list have extra space between items?
A blank line between any two items makes the whole list loose, which wraps every item in a paragraph and adds vertical space. Remove the blank lines between items to get a tight list.
Why is my Markdown list not rendering?
Check for a missing space after the marker, a child indented less than its parent's text, a numbered list starting at something other than 1 directly under a paragraph, or a chat app that does not support list syntax in that context.
Do Discord and Slack support Markdown lists?
Discord does: - or * for bullets, 1. for numbers, and 2 spaces before the marker to indent. Slack's composer builds a list when you type * or 1. followed by a space, but text sent by apps as mrkdwn has no list syntax.