Markdown lists: ordered, unordered, nested, and task lists
Every way to write a list in Markdown — unordered bullets, ordered numbers, nested lists, task lists, and the rules that decide what renders.
A list in Markdown looks obvious - until you try to nest one, mix ordered and unordered, or include a paragraph inside a list item. Then the indentation rules matter. This guide covers every list type in Markdown, the rules that make them work, and the common ways they break.
Unordered (bullet) lists
- First item
- Second item
- Third item
Renders as bullets. -, *, and + are all valid bullet markers. Most style guides prefer - because it reads cleanest in source. Pick one and stick with it within a document.
- Same renderer
* Same renderer
- Same renderer
All three produce identical output. Mixing them in the same list is technically legal but produces unpredictable behavior in some parsers - don't.
Ordered (numbered) lists
1. First item
2. Second item
3. Third item
The number you write doesn't have to match the rendered number. This:
1. First
1. Second
1. Third
…also renders as 1, 2, 3. Renderers auto-number from the starting integer. This is useful when you're rearranging list items often - you don't have to renumber.
To start an ordered list at a number other than 1, use the start value:
5. Fifth item
6. Sixth item
CommonMark and most renderers honor the start number. Some parsers always start at 1.
Nested lists
Indent the nested items by 2 or 4 spaces (depending on the parser):
- Parent item
- Nested item (2-space indent)
- Deeper nested item (4-space indent)
- Another parent
The most common bug: using a single tab or a single space for nesting. Most parsers want exactly 2 spaces per level (for - bullets) or 3 spaces (for 1. ordered items, to align with the digit + dot + space). When in doubt, use 4 spaces - it works in every parser.
Mixing ordered and unordered nesting works:
1. First parent
- Bullet under #1
- Another bullet
2. Second parent
1. Nested ordered
2. Nested ordered
Task lists (GitHub Flavored Markdown)
- [ ] Unchecked task
- [x] Completed task
- [ ] Another unchecked
- [x] Nested completed
Renders as interactive checkboxes on GitHub, GitLab, and most modern Markdown renderers. CommonMark itself doesn't define task lists - they're a GitHub Flavored Markdown extension. Tools that follow strict CommonMark show them as literal [ ] and [x] characters.
Practical uses:
- Issue checklists
- PR checklists ("ready to merge when:")
- README progress trackers
- Personal todo lists in Obsidian / Notion / Bear
Paragraphs inside list items
A common gotcha - you want a paragraph break inside a list item:
- First item.
This second paragraph belongs to the first item.
Note the blank line and the 2-space indent.
- Second item.
Without the blank line, parsers treat the second paragraph as part of the same line. Without the indent, parsers treat the second paragraph as a sibling element, not a child.
Code blocks inside list items
Indent the fenced block to match:
1. First step:
```python
def hello():
print("inside the list")
```
2. Second step.
The 3-space indent matches the start of "First step" - the text after 1. . The blank line before the fenced block is required by some parsers.
See Markdown code blocks for the full code-fence rules.
Lists in Discord and Slack
- Discord supports
-,*, and+for unordered and1.for ordered. Nesting works with two-space indent. No task lists. See Markdown in Discord. - Slack supports
-and1.for bullets and ordered. No nesting beyond one level. No task lists. See Markdown in Slack.
Lists in tables
Markdown tables don't reliably render lists inside cells. The standard workaround: use HTML <br> for line breaks within a cell, then format as comma-separated. If you need a real list-in-a-cell, write it in Markdown, then convert the whole doc to HTML via Markdown to HTML, then style the cell content with CSS.
The common AI failure: stray bullet characters
AI assistants love to use Unicode bullet characters - •, ‣, ▪︎ - instead of the ASCII - or * that Markdown understands. Result: the "list" renders as paragraphs with a leading bullet character.
• Item one ← renders as paragraph with leading bullet
• Item two ← renders as paragraph with leading bullet
Versus the right syntax:
- Item one ← renders as actual list
- Item two ← renders as actual list
The AI Markdown cleanup checklist covers this and the 11 other artifacts. The fastest fix: paste into Markdown Tidy and click Tidy - the bullet normalizer rewrites Unicode bullets back to - in one pass.
Quick reference
- Bullet
* Same bullet
- Same bullet
1. Numbered
1. Auto-renumbered
1. Auto-renumbered
1. Start at five
1. Continue
- Nested
- Two spaces deeper
- Four spaces deeper
- [ ] Task
- [x] Done
- Paragraph in item.
Blank line + 2-space indent for continuation.
For the rest of Markdown syntax in one place, see the complete Markdown syntax cheat sheet.
Related articles
Introducing the Markdown Tidy API: programmatic clean, repair and convert
The Markdown Tidy API — one endpoint, X-API-KEY auth, a free tier with 50 credits per month and 2,000 with Premium, the same conversion engine that powers the web app.
Markdown in React: rendering, sanitization, and the libraries that matter
How to render Markdown in a React app — react-markdown, MDX, and the security trade-offs. With code snippets you can paste into a project today.
Multilingual Markdown: handling German, Japanese, French and Spanish content cleanly
AI assistants handle multilingual content well. Documents often do not. Here's what tends to break — and how — when exporting non-English Markdown to PDF or DOCX.
README.md: a writing guide with examples (2026)
A README is your project's storefront. The structure that works, the sections that matter, and the patterns that make a README convert a curious visitor into a user.