How to Format Code Blocks in Markdown Files
Learn how to format code in Markdown with fenced code blocks and language tags for JSON and Python, plus how to check the result before you publish.
If you have ever pasted a JSON response or a Python script into a Markdown file and watched it turn into a jumble of bold text, bullet points and stray asterisks, you have run into the main problem: Markdown reads your code as prose unless you tell it otherwise. The fix is a fenced code block. Once you wrap the snippet correctly, the text keeps its spacing, stops being formatted, and gets a label that shows readers which language it is written in.
This guide is for people writing README files, technical notes, tutorials, or documentation who need to know how to format code in Markdown without guessing. It focuses on the two formats readers ask about most: JSON and Python. The general Markdown syntax is covered elsewhere, so here we stick to code blocks, language tags, and the checks that catch the mistakes that cause broken output.
How do you format code in Markdown? The short answer
Put the code between two lines that each contain three backticks, and add a language name after the opening line. That is a fenced code block, and it works in most Markdown renderers. For a short fragment inside a sentence, use single backticks instead.
| Your situation | What to do | Why |
|---|---|---|
| A multi-line JSON example | Open with three backticks and the word json, then close with three backticks | Keeps indentation and quotes intact and applies JSON labeling |
| A multi-line Python script | Open with three backticks and the word python, then close with three backticks | Preserves line breaks and indentation, which Python depends on |
| A variable name or short value in a sentence | Wrap it in single backticks, such as user_id | Keeps it visually distinct without breaking the paragraph |
| A snippet with no specific language | Use three backticks with no language word | Still shows as a code block, just without syntax labeling |
| Code inside a numbered or bulleted list | Indent the fence to line up with the list item's text | Keeps the block attached to the list item instead of ending the list |
Before you start
Before you write the block, gather a few things. Each one prevents a common problem.
- The exact code, copied from a working source. Retyping a snippet introduces typos and changes quotation marks. Copy it from your editor or terminal so the characters match what the code needs to run.
- The language you are labeling. Use
jsonfor JSON,pythonfor Python, and so on. Lowercase names are the convention and match what most renderers expect. - A Markdown preview or the place the file will be published. Some renderers handle language tags, line wrapping, and horizontal scrolling differently. Know where readers will see the document so you can check it.
- A plain text editor, or an editor that does not auto-correct. Some word processors replace straight quotes with curly quotes and double hyphens with dashes. Curly quotes break JSON and Python, so use a plain text editor or a Markdown-aware editor.
- Permission to change the code, if it is not yours. If you are quoting someone else's snippet, keep the code exactly as written and name the source according to the license or your team's rules.
Writing a JSON or Python code block, step by step
The steps below work for both formats. Only the language tag changes.
- Place the cursor on a blank line. Start the block on its own line, with a blank line above it. Many renderers need that gap to recognize the block, and it keeps the code separate from the paragraph before it.
- Type three backticks, then the language name. For JSON, type three backticks followed directly by
json. For Python, usepython. The language name tells the renderer how to label and, in many cases, color the code. - Paste the code exactly as it is. Leave the indentation alone. JSON does not require indentation, but readers expect it, and Python will fail to run if you change it. Do not add bullet markers or extra asterisks inside the block, because they become part of the code.
- Type three backticks on a new line to close the block. The closing fence must use the same number of backticks as the opening one. Put it on its own line, with nothing else on that line.
- Add a short sentence before or after the block. Explain what the snippet does or what the reader should see. A code block alone can leave readers guessing about its purpose.
- Use single backticks for inline references. If you mention a key such as
"status"or a function such asprint()in a sentence, wrap it in single backticks rather than starting a block. - Indent the fence when the block sits inside a list. If the code belongs to a numbered step, indent the opening fence, code, and closing fence so they line up with the text of that step. An unindented block ends the list and starts a new section.
- Save the file with a .md extension. Plain text saved as .md is what most Markdown tools expect. A .txt file will not render as Markdown in the same way.
If you want to see how the block looks before you publish, paste the file into the UniDoc web editor at app.unidoc.top, which supports Markdown. You can also check the result in whatever renderer your team uses.
Check the result
Once the file renders, look at each code block. The table below covers the usual problems.
| Check | How to see it | If it's wrong |
|---|---|---|
| The block starts and ends where you expect | Scroll through the rendered page and confirm the code stops at the closing fence | If the rest of the page is shaded or monospaced, the closing fence is missing or has extra characters |
| The language label is correct | Look for the language name on the block, or check that colors match the syntax | Fix the tag spelling, such as Python instead of python, if your renderer depends on it |
| JSON is valid | Run the snippet through a JSON validator or your code editor's JSON check | Remove trailing commas, replace curly quotes with straight quotes, and make sure keys use double quotes |
| Python indentation is intact | Compare the rendered code with your source file line by line | Restore spaces or tabs that were changed; mixing them can cause errors |
| Curly quotes did not sneak in | Search the file for curly quotation marks | Replace them with straight quotes in the source before republishing |
| Lists and surrounding text are not disturbed | Check the paragraphs above and below each block | Add a blank line before the opening fence or re-indent it to match the list item |
If you translate the Markdown file, check the code blocks again afterward. OmniDoc's document translation accepts Markdown files and keeps the layout, but code is still text, so review the code blocks for changed characters, and confirm that any words inside the code are the ones you intended to keep. Machine translation can make mistakes, so check important content before publishing.
❓ FAQ
1. What if my code already contains three backticks?
Use a longer fence on the outside, such as four backticks, and close it with the same four. The inner three backticks then appear as ordinary text inside the block. Keep the opening and closing fences the same length.
2. Which language names can I use besides json and python?
Common names include bash, javascript, yaml, sql, and markdown. Use the name your readers would recognize, and keep it lowercase so it matches the usual convention. If a renderer does not highlight a language, the block still displays as code.
3. Can I use indentation instead of backticks?
Some Markdown renderers accept a code block made by indenting each line by four spaces. It works, but it has no room for a language tag, and it is easy to break when the block sits inside a list. Fenced blocks with a language name are the more reliable choice for JSON and Python.
📝 Summary
To format code in Markdown, wrap it in a fenced block with a language tag such as json or python, and close the block with a matching line of three backticks. Use single backticks for short references inside sentences, and check each block in the rendered output for missing fences, invalid JSON, and changed indentation.


