Python Syntax Errors Explained

Discover common Python syntax errors and how to fix them. Learn proactive strategies to prevent errors and reactive methods to resolve them efficiently.
16 min read
Python Syntax Errors Explained blog image

Every language has a set of rules defining how to properly form valid constructs; this is referred to as the language’s syntax. When you’re just learning how to code, experiencing syntax errors is part of the process. Beginners often struggle to understand the syntax rules and frequently encounter typographical errors and misplaced symbols.

Syntax errors are a common part of everyone’s coding journey, but the sooner you understand why they occur, the sooner you can fix them.

In this article, you’ll learn about different syntax errors in Python and how to avoid them.

Syntax Errors in Python

In any programming language, failing to follow the syntax rules most likely results in a syntax error, and your code can’t run.

In Python, the Python Interpreter reads and executes your Python code, acting as a translator between high-level Python and the low-level machine language your computer understands. If your code doesn’t follow Python’s syntax rules, the interpreter can’t process the code.

When the Python interpreter encounters a syntax error, it halts and displays an error message. This message includes a traceback to the line of code that caused the error, along with an indicator pointing to the earliest point in the line where the error was detected.

The interpreter tries to provide you with as much relevant information as possible to help you diagnose and fix the issue, so make sure you read your error messages carefully.

Syntax errors in Python are all about structure—they occur when a command violates the language’s grammatical rules. For instance, in English, a sentence must always begin with a capital letter and end with a punctuation mark. Similarly, in Python, a statement must always end with a new line and blocks of code (like those in if statements or loops) that must be indented correctly.

If you’re familiar with runtime errors, you may be wondering how they differ from syntax errors. Syntax errors prevent a program from running. Runtime errors occur after the program has started running.

Exploring Different Types of Syntax Errors

Because Python has a lot of syntax rules, a lot of syntax errors can also occur. In this section, you’ll learn about several common errors and solutions.

Misplaced, Missing, or Mismatched Punctuation

Python uses various punctuation marks to understand the structure of your code. You need to make sure each of these punctuation marks is placed correctly and matched with the corresponding punctuation to avoid syntax errors.

For instance, you should always use parentheses (()), brackets ([]), and braces ({}) in matching pairs. That means if you open one, you must close it.

In the following example, a curly brace is used to define an object, but it isn’t closed:

# Incorrect
proxies = {
    'http': proxy_url,
    'https': proxy_url

If you try to run this, the interpreter throws a SyntaxError:

File "python-syntax-errors.py", line 2
    proxies = {
            ^
SyntaxError: '{' was never closed

As mentioned previously, the Python interpreter usually provides a descriptive error message. Here, you’re given the name of the file where the error occurred, the line number where it occurred, and an arrow pointing to where in the code the error was detected. You’re also told that '{' was never closed.

With all this information, you can easily decipher that you need to close the curly bracket to fix the problem:

# Correct
proxies = {
    'http': proxy_url,
    'https': proxy_url
} # Closed a curly bracket

Another punctuation mark that often causes issues is quotes (’ or “). Python, like many other programming languages, uses quotes to define strings. You must use the same type of quote to open and close a string:

# Incorrect
host = "brd.superproxy.io'

Mixing up single and double quotes results in a syntax error:

File "python-syntax-errors.py", line 2
    host = "brd.superproxy.io'
        ^
SyntaxError: unterminated string literal (detected at line 2)

Here, the interpreter tells you that you haven’t terminated the string literal in the second line:

# Correct
host = "brd.superproxy.io"

You can use a pair of single quotes to get the same result.

In some scenarios, you may need to use single and double quotes in a string. In that case, you can use triple quotes like this:

quote = """He said, "It's the best proxy service you can find!", and showed me this provider."""

In Python, commas are used to separate items in a list, tuple, or function argument. Missing a comma can lead to unexpected results:

# Incorrect
proxies= [
    {"http": "http://123.456.789.1:8080", "https": "https://123.456.789.1:8080"}
    {"http": "http://98.765.432.1:3128", "https": "https://98.765.432.1:3128"}
    {"http": "http://192.168.1.1:8080", "https": "https://192.168.1.1:8080"}
]

Running this code results in the following error message:

File "python-syntax-errors.py", line 3
{"http": "http://123.456.789.1:8080", "https": "https://123.456.789.1:8080"}
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
SyntaxError: invalid syntax. Perhaps you forgot a comma?

While error messages are made as helpful as they can be, they might not always suggest perfect solutions. This snippet misses four commas, but the error message picks out only the first instance. To fix this, you should look at the code around the error message and find other places where you might have forgotten to place a comma:

# Correct
proxies = [
    {"http": "http://123.456.789.1:8080", "https": "https://123.456.789.1:8080"},
    {"http": "http://98.765.432.1:3128", "https": "https://98.765.432.1:3128"},
    {"http": "http://192.168.1.1:8080", "https": "https://192.168.1.1:8080"}
]

In contrast to commas, colons are used to start a new block of code (like in an if statement or for loop):

import requests
from bs4 import BeautifulSoup

# Incorrect
response = requests.get('https://example.com')
if response.status_code == 200
    soup = BeautifulSoup(response.content, 'html.parser')
    title = soup.title.text
    print(title)
)

Forgetting a colon results in the following syntax error:

if response.status_code == 200
    ^
SyntaxError: expected ':'   

From this error message, it’s easy to determine that there’s a colon missing, and you can add it in the suggested place to fix the issue:

import requests
from bs4 import BeautifulSoup

# Correct
response = requests.get('https://example.com')
if response.status_code == 200:
    soup = BeautifulSoup(response.content, 'html.parser')
    title = soup.title.text
    print(title)

Misspelled, Misplaced, or Missing Python Keywords

Python keywords are special words reserved for specific meanings and uses, and you can’t use them as variable names. If you misspell, misplace, or forget to use a keyword, the interpreter raises an error.

For instance, if you’re trying to import the requests and pprint modules into your web scraping project, you may accidentally misspell the import keyword:

# Incorrect
improt requests
import pprint

This misspelling causes the interpreter to raise the following invalid syntax error:

File "python-syntax-errors.py", line 2
    improt requests
        ^^^^^^^^
SyntaxError: invalid syntax

Unfortunately, this error message is vague, so you have to do a little work to figure out what went wrong. You can see the arrows in the error message point to requests; that’s where the interpreter first detected a syntax error. Since misspelling the name of a module doesn’t raise a syntax error, the only other option is that you misspelled the import keyword.

A simple correction of the word import fixes the error:

# Correct
import requests
import pprint

It’s also possible to mess up the from ... import … statement like this:

import BeautifulSoup from bs4

Although it seems okay, running the preceding code results in an error because the from keyword should go before import:

File "python-syntax-errors.py", line 2
import BeautifulSoup from bs4
    ^^^^
SyntaxError: invalid syntax

Switching from and import fixes the issue:

from bs4 import BeautifulSoup

Missing a keyword is another issue you’ll probably face when coding in Python. This type of error is a bit more subtle than the other errors mentioned because missing a keyword in Python can throw different errors.

If you forget to include the return keyword in a function that is supposed to return a value, the function doesn’t behave as expected:

def fetch_data():
    response = requests.get('https://example.com')
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    # Missing a return statement here
    
data = fetch_data()

This does not throw a syntax error, but the function returns None instead of the expected result. Adding the return keyword fixes the preceding code:

def fetch_data():
    response = requests.get('https://example.com')
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    return data

data = fetch_data()

If you forget the def keyword when defining a function, you encounter a syntax error:

# Missing the `def` keyword
fetch_data():
    response = requests.get('https://example.com')
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    return data

data = fetch_data()

The preceding code raises a syntax error because the interpreter expects a keyword before the function name:

File "python-syntax-errors.py", line 1
   fetch_data():
               ^
SyntaxError: invalid syntax

Adding the def keyword resolves the error:

def fetch_data():
    response = requests.get('https://example.com')
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    return data

data = fetch_data()

If you forget the if keyword in a conditional statement, the interpreter raises an error because the interpreter expects a keyword before the condition:

import requests
from bs4 import BeautifulSoup

response = requests.get('https://example.com')
# Missing the if keyword
response.status_code == 200:
    soup = BeautifulSoup(response.content, 'html.parser')
    title = soup.title.text
    print(title)
File "python-syntax-errors.py", line 6
   response.status_code == 200:
                              ^
SyntaxError: invalid syntax

You just need to include the if keyword to fix this issue:

import requests
from bs4 import BeautifulSoup

response = requests.get('https://example.com')
if response.status_code == 200:
    soup = BeautifulSoup(response.content, 'html.parser')
    title = soup.title.text
    print(title)

Note that these are just a few examples of missing keywords in Python. Missing keywords can throw other kinds of errors, too, so be extra careful.

Incorrect Use of the Assignment Operator

In Python, the = symbol is used for assignments, and == is used for comparisons. Mixing these two symbols up can lead to a syntax error:

import requests
from bs4 import BeautifulSoup

# Incorrect
response = requests.get('https://example.com', proxies=proxies)
if response = requests.get('https://example.com/data', proxies=proxies):
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    for item in data:
    print(item.text)
else:
    print("Failed to retrieve data")

In the previous code, the interpreter correctly detects what caused the problem:

File "python-syntax-errors.py", line 5
if response = requests.get('https://example.com/data', proxies=proxies)
     ^^^^^^

In this instance, you’re trying to verify that your response is the same as the response to the request.get() method. That means you need to replace the assignment operator in the if statement with the comparison operator:

import requests
from bs4 import BeautifulSoup

# Correct
response = requests.get('https://example.com', proxies=proxies)
# Change in the following line
if response == requests.get('https://example.com/data', proxies=proxies):
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    for item in data:
    print(item.text)
else:
    print("Failed to retrieve data")

Indentation Errors

Python uses indentation to define blocks of code. If your code is not indented correctly, the interpreter can’t distinguish the content of the code block and raises an IndentationError:

# Incorrect
async with async_playwright() as playwright:
await run(playwright)

As you can see in the previous code, there’s no indentation after the definition of a block (colon), so when you run this, you get the following error message:

File "python-syntax-errors.py", line 2
    await run(playwright)
    ^
IndentationError: expected an indented block after the with statement on line 1

To fix this problem, follow Python’s syntax rules and indent the code block correctly:

# Correct
async with async_playwright() as playwright:
    await run(playwright)

Issues with Variable Declarations

Variable names in Python must start with a letter or an underscore, and they can contain only letters, numbers, and underscores. Additionally, Python is case-sensitive, so myvariablemyVariable, and MYVARIABLE are all different variables.

Your variable names can never start with anything except a letter or an underscore. The following variable name starts with 1, which does not comply with Python’s syntax rules:

# Incorrect
1st_port = 22225

When you run the preceding code, the interpreter raises a SyntaxError:

File "python-syntax-errors.py", line 2
    1st_port = 1
    ^
SyntaxError: invalid decimal literal

To fix this, you must start the variable name with a letter or an underscore. Any of the following options can work:

# Correct
first_port = 22225
port_no_1 = 22225

Function Definition and Call Errors

When defining a function, you must use the def keyword, followed by the function name, parentheses, and a colon. When calling a function, you must use its name followed by parentheses. Forgetting any of these elements raises a syntax error:

import requests
from bs4 import BeautifulSoup

# Incorrect
def fetch_data
response = requests.get('https://example.com')
soup = BeautifulSoup(response.content, 'html.parser')
data = soup.find_all('div', class_='data')
return data

# Incorrect
data = fetch_data

Here, three elements are missing, and each of them causes a separate syntax error. To fix these errors, you need to add parentheses and a colon after the function name fetch_data. You also need to add parentheses after the function call on the last line of the code block, like this:

import requests
from bs4 import BeautifulSoup

# Corrected
def fetch_data():
    response = requests.get('https://example.com')
    soup = BeautifulSoup(response.content, 'html.parser')
    data = soup.find_all('div', class_='data')
    return data

# Corrected
data = fetch_data()

Note that missing parentheses and colons in the function definition always causes a syntax error. However, the interpreter doesn’t pick up whether you forgot the parentheses when calling a function (fetch_data()). In that case, it doesn’t necessarily throw an exception, which can lead to unexpected behavior.

Best Practices to Help You Avoid Syntax Errors

Writing error-free code is a skill that comes with practice. Understanding and implementing the following best practices can help you avoid common syntax errors.

Proactive Strategies

The best way to deal with syntax errors is to try and prevent them in the first place.

Before you start working on a project, you should be familiar with the most common syntax rules of the language you’re coding in.

Use a Code Editor with Syntax Highlighting and Indentation Checking

A good code editor is a great partner when it comes to avoiding syntax errors. Most modern code editors offer features like syntax highlighting and indentation checking, which can help you spot errors before you run your code.

For example, in the following illustration, there’s a red mark at the end of the if response.status_code == 200 line that suggests that there’s an error since there’s no colon:

A red mark suggesting there is an error

Follow Consistent Coding Style Guidelines

As with most things, consistency is key when it comes to writing clean, error-free code. Aim to follow a consistent coding style. This makes your code easier to read and understand, which in turn makes it easier to spot and fix errors.

In Python, the PEP 8 Style Guide is widely accepted as the standard for coding style. It provides guidelines for things like variable naming, indentation, and the use of white space.

Write Code in Small, Well-Defined Functions

Breaking your code down into small, well-defined functions can make it easier to manage and debug.

Each function should have a single, clear purpose. If a function does too many things, it can become difficult to understand and debug. For example, take a look at the following scrape_and_analyze() function:

import requests
from bs4 import BeautifulSoup
from textblob import TextBlob

def scrape_and_analyze():
    url = "https://example.com/articles"
    response = requests.get(url)
    soup = BeautifulSoup(response.content, "html.parser")
    titles = soup.find_all("h2", class_="article-title")
    sentiments = []
    for title in titles:
    title_text = title.get_text()
    blob = TextBlob(title_text)
    sentiment = blob.sentiment.polarity
    sentiments.append(sentiment)
    return sentiments

print(scrape_and_analyze())

In this example, it would be more readable to break down this function into multiple smaller ones, each executing a smaller, more manageable portion of code:

import requests
from bs4 import BeautifulSoup
from textblob import TextBlob

def scrape_titles(url):
    """Scrape article titles from a given URL."""
    response = requests.get(url)
    soup = BeautifulSoup(response.content, "html.parser")
    titles = soup.find_all("h2", class_="article-title")
    return [title.get_text() for title in titles]

def analyze_sentiment(text):
    """Analyze sentiment of a given text."""
    blob = TextBlob(text)
    return blob.sentiment.polarity

def analyze_titles_sentiment(titles):
    """Analyze sentiment of a list of titles."""
    return [analyze_sentiment(title) for title in titles]

def scrape_and_analyze(url):
    """Scrape titles from a website and analyze their sentiment."""
    titles = scrape_titles(url)
    sentiments = analyze_titles_sentiment(titles)
    return sentiments

url = "https://example.com/articles"
print(scrape_and_analyze(url))

Reactive Strategies

No matter how hard you try to prevent errors, a few can always sneak through. The following strategies focus on dealing with these errors.

Read Error Messages Carefully

As previously mentioned, Python usually gives you an error message that includes information about the nature of the error and its location.

Carefully reading these error messages can give you valuable clues about what went wrong and how to fix it.

Use Print Statements Strategically

Using print() statements is a quick and effective way to debug small projects or simple issues where you need to trace the flow of execution or inspect variable values at specific points. It’s particularly useful for rapid development and when you have a good understanding of where the problem might lie.

Print debugging can be less intrusive and faster to implement, making it a go-to method for quick fixes and straightforward bugs. However, always be aware that it’s for temporary use only, and make sure not to use it in the production code since printing data shown to end users can lead to catastrophic data leaks and performance issues.

For when you have more complex issues, have larger codebases, or need to inspect the state of the program more deeply (such as variable states across multiple function calls or iterations), using a debugger is more appropriate. Debuggers allow you to set break points, step through code line-by-line, and inspect the state of the application at any point, providing a more controlled and comprehensive debugging environment.

Leverage Online Resources and Communities

If you’re stuck on a particularly tricky error, don’t hesitate to seek help. There are numerous online resources (Python Docs and Real Python) and communities (r/Python and r/LearnPython subreddits, Stack Overflow, and Python Forum) where you can find answers and solutions to your problems.

Conclusion

In this article, you’ve explored the world of Python syntax errors. You learned about a few types of syntax errors, including where they can occur and how to identify and fix them.

You also learned about a few proactive and reactive strategies to help you prevent syntax errors or fix them when they occur.

Bright Data is a leading provider of web scraping tools. Whether you need reliable proxies, automated data collection, ready-to-use datasets, or automation of web scraping tasks, Bright Data offers solutions that can make your web scraping projects more efficient and productive.

Sign up now to find the right product for your needs and start a free trial today!

No credit card required