SyntaxError
Core Python Errors and Exceptions Error explained

Python SyntaxError

1SyntaxError: overview

A SyntaxError means Python could not parse your code because it breaks the language's grammar, so the whole file is rejected before any line runs.

GoalBy the end you can read a SyntaxError message and caret, spot the six most common grammar mistakes and fix each one.

Before this lesson: Python Syntax, Python Exceptions: try, except, else and finally

2SyntaxError: diagram

Python SyntaxErrorBroken: nothing runsscore = 72print('Starting...')if score > 50 print('pass')# SyntaxError: expected ':'# 'Starting...' never printsFixed: runs top to bottomscore = 72print('Starting...')if score > 50: print('pass')# Starting...# passadd :
Python checks the grammar of the whole file first. One missing colon stops everything, including lines above the mistake that were perfectly fine.

3SyntaxError: explained step by step

A SyntaxError means Python could not understand the grammar of your code. Unlike most errors, it is raised before the program starts: Python reads the entire file first, and if any line breaks the rules, none of the file runs, not even the lines above the mistake.

To show this safely on the page, the examples below pass code as text to compile(), which checks the grammar without running it. In your own file you would simply see the traceback.

Python
source = 'print("Starting...")\nif score > 50\n    print("pass")'
try:
    compile(source, "main.py", "exec")
except SyntaxError as err:
    print("SyntaxError:", err.msg)
    print("line:", err.lineno, "column:", err.offset)
    print("text:", err.text.strip())

"Starting..." was never printed, because the whole file was rejected first.

How to read a SyntaxError and its caret

  File "main.py", line 2
    if score > 50
                 ^
SyntaxError: expected ':'
  1. The last line is the message. Recent Python versions are specific: expected ':', '(' was never closed, unterminated string literal.
  2. The line above shows the code, and the ^ caret points to where Python gave up, which is often just after the real mistake.
  3. If the reported line looks perfectly fine, check the line before it. An unclosed bracket or a missing quote makes Python swallow the next line, so the complaint arrives late.

Why a missing colon causes SyntaxError

if, elif, else, for, while, def, class and try all end with a colon, which tells Python that an indented block follows. See Python if/else and Python functions for the full shapes.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show('if score > 50\n    print("pass")')
show('def greet(name)\n    return name')
show('if score > 50:\n    print("pass")')

Unclosed or mismatched brackets in Python

Every (, [ and { needs its partner. Python reports an unclosed bracket at the line where it was opened, even if the code that confused it is lower down.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show('total = (4 +\n    tax\nprint(total)')
show('x = 1 + 2)')
show('values = [1, 2, 3)')
show('total = (4 +\n    5)')

Unterminated string literal errors

A string that opens with a quote must close with the same quote on the same line. An apostrophe inside single quotes ends the string early; use double quotes around the text, or escape the apostrophe. The same rule applies to f-strings, where an empty {} is an error. More about text in Python strings.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show("print('It's ready')")
show('print("It\'s ready")')
show('name = "Asha')
show('label = f"Total: {}"')

Missing comma between items

In a list, dictionary or call, forgetting a comma gives invalid syntax. Perhaps you forgot a comma?. Beware the one case where Python does not complain: two string literals side by side are silently joined, so ["red" "blue"] is a list with one item, "redblue". See Python lists.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show("prices = [4, 5 6]")
print(["red" "blue", "green"])

Using = instead of == in a condition

A single = assigns; == compares. Putting = inside an if or while condition is a SyntaxError, and so is assigning to a literal. See Python operators.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show("if answer = 5:\n    pass")
show("5 = answer")
show("if answer == 5:\n    pass")

Reserved words and Python 2 code

Keywords such as class, for, def, in and True cannot be variable names. Older tutorials use print "hi" without parentheses, which Python 3 rejects.

Python
def show(source):
    try:
        compile(source, "main.py", "exec")
        print("OK")
    except SyntaxError as err:
        print(f"line {err.lineno}: {err.msg}")

show('class = "Maths"')
show('print "hello"')
show('print("hello")')

If the message instead says IndentationError, the grammar was fine but the spacing was not; see Python IndentationError. If the code parses but a name is missing, you get a NameError, and the basic grammar rules are in Python syntax.

4SyntaxError: syntax

if condition:               # block statements end with a colon
    ...
total = (a + b)             # every ( [ { needs its partner ) ] }
name = "It's fine"          # open and close a string with the same quote
items = [1, 2, 3]           # commas between items
if x == 5:                  # == compares, = assigns
print("hello")              # Python 3 print needs parentheses
compile(source, "main.py", "exec")   # check grammar without running

5SyntaxError: run the example

Press Run (or Ctrl + Enter). The output (step 6) appears directly below the code. Change anything and run it again.

Interactive example
def check(label, source):
    try:
        compile(source, "<demo>", "exec")
        print(f"{label}: ok")
    except SyntaxError as err:
        print(f"{label}: line {err.lineno} - {err.msg}")

check("missing colon", "score = 72\nif score > 50\n    print('pass')")
check("fixed colon", "score = 72\nif score > 50:\n    print('pass')")
check("open bracket", "total = (4 +\n    5\nprint(total)")
check("bad string", "name = 'Asha")
check("assign in if", "if score = 50:\n    pass")
Expected outputmissing colon: line 2 - expected ':'
fixed colon: ok
open bracket: line 1 - '(' was never closed
bad string: line 1 - unterminated string literal (detected at line 1)
assign in if: line 1 - invalid syntax. Maybe you meant '==' or ':=' instead of '='?

7SyntaxError: how the example works

Hover or tap a step to highlight its lines in the example above.

  1. Line 1-6check() hands source text to compile(), which parses it without running it. A SyntaxError carries lineno (the line) and msg (the explanation); the function prints both.
  2. Line 8The if line has no colon, so Python reports expected ':' on line 2 of the snippet.
  3. Line 9The same snippet with the colon added compiles successfully.
  4. Line 10An opening bracket that is never closed is reported on the line where the bracket was opened, not where Python noticed the problem.
  5. Line 11A string that starts with a quote and never ends gives unterminated string literal.
  6. Line 12= inside a condition is rejected, and Python suggests the comparison operator ==.

8SyntaxError: common mistakes

Leaving out the colon

✗ Wrong

score = 72
if score >= 50
    print("pass")
File "main.py", line 2 if score >= 50 ^ SyntaxError: expected ':'

✓ Right

score = 72
if score >= 50:
    print("pass")

Statements that start a block (if, for, while, def, class, else) must end with a colon.

An unclosed parenthesis

✗ Wrong

prices = [4, 6]
print("Total:", sum(prices)
print("Done")
File "main.py", line 2 print("Total:", sum(prices) ^ SyntaxError: '(' was never closed

✓ Right

prices = [4, 6]
print("Total:", sum(prices))
print("Done")

Python points at the bracket that was opened and never closed. Add the missing ) at the end of that statement.

An apostrophe inside single quotes

✗ Wrong

message = 'Don't forget your ticket'
SyntaxError: unterminated string literal (detected at line 1)

✓ Right

message = "Don't forget your ticket"
print(message)

The apostrophe ends the string early. Wrap the text in double quotes, or escape the apostrophe as \'.

Using = in a condition

✗ Wrong

age = 20
if age = 18:
    print("Exactly 18")
SyntaxError: invalid syntax. Maybe you meant '==' or ':=' instead of '='?

✓ Right

age = 20
if age == 18:
    print("Exactly 18")

= assigns a value; == compares two values. A condition needs the comparison.

Using a keyword as a variable name

✗ Wrong

class = "Maths 101"
print(class)
SyntaxError: invalid syntax

✓ Right

course = "Maths 101"
print(course)

class is reserved for defining classes. Pick another name such as course or class_name.

9SyntaxError: exercises

Write your answer, then press Check. The checks run in your browser.

1. Fix the two syntax errors

Fix the bug Easy

This program should print Total: 19.5, but Python rejects it before running anything. There are two grammar mistakes: fix both. total_price(prices) must return the sum and basket must stay [4.5, 3, 12].

Your code
def total_price(prices)
    return sum(prices)

basket = [4.5, 3, 12
print("Total:", total_price(basket))

2. Predict the compile results

Predict the output Easy

Read the code and type exactly what it prints. Remember that Python reports an unclosed bracket on the line where it was opened. Then press Check.

Read this code
snippets = [
    "x = 10",
    "if x > 5",
    "a = 1\nb = [2,\n3",
    "print('ok')",
]

for source in snippets:
    try:
        compile(source, "<snippet>", "exec")
        print("ok")
    except SyntaxError as err:
        print("error on line", err.lineno)

2 more exercises → 6 more examples

Finished this lesson?
Progress is saved in this browser — create a free account to keep it across devices.

Questions learners ask

Why does Python say invalid syntax on a line that looks correct?

Python reports the place where it gave up, which can be after the real mistake. Check the line before for a missing closing bracket, quote or comma. Newer versions often say which bracket was never closed, so read the full message, not just the caret.

Can I catch a SyntaxError with try/except?

Not in the same file, because the file is rejected before any code runs. You can catch it when the broken code comes in as text, using compile(), exec(), eval() or ast.parse() inside try/except SyntaxError.

What is the difference between SyntaxError and IndentationError?

IndentationError is a subclass of SyntaxError for problems with leading spaces, such as a missing indented block or inconsistent tabs. SyntaxError covers every other grammar problem, such as missing colons, brackets or quotes.

Further reading

10Next lesson

Up nextPython IndentationErrorAn IndentationError means the spaces at the start of a line don't match the block structure Python expected, for exampl…

Related:
Python SyntaxPython Exceptions: try, except, else and finallyPython NameErrorPython IndentationError

← Python NameError · All Errors and Exceptions lessons · Practise in the IDE