DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Zones

Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks

Low-Code Development: Leverage low and no code to streamline your workflow so that you can focus on higher priorities.

DZone Security Research: Tell us your top security strategies in 2024, influence our research, and enter for a chance to win $!

Launch your software development career: Dive head first into the SDLC and learn how to build high-quality software and teams.

Open Source Migration Practices and Patterns: Explore key traits of migrating open-source software and its impact on software development.

Related

  • An Overview of Creating Databases With Python
  • DocRaptor vs. WeasyPrint: A PDF Export Showdown
  • How to Create Your Own Cryptocurrency Blockchain in Python
  • Alexa Skill With Python

Trending

  • Explore the Complete Guide to Various Internet of Things (IoT) Protocols
  • Empowering Citizen Developers With Low- and No-Code Tools: Changing Developer Workflows and Empowering Non-Technical Employees to Build Apps
  • Unlocking Potential With Mobile App Performance Testing
  • Maintain Chat History in Generative AI Apps With Valkey
  1. DZone
  2. Coding
  3. Tools
  4. Linting Excellence: How Black, isort, and Ruff Elevate Python Code Quality

Linting Excellence: How Black, isort, and Ruff Elevate Python Code Quality

In this article, explore Black, isort, and Ruff to streamline Python code quality checks and ensure consistent coding standards.

By 
Prince Bose user avatar
Prince Bose
·
Pavan Vemuri user avatar
Pavan Vemuri
·
Tharakarama Reddy Yernapalli Sreenivasulu user avatar
Tharakarama Reddy Yernapalli Sreenivasulu
·
Jul. 04, 24 · Presentation
Like (4)
Save
Tweet
Share
1.8K Views

Join the DZone community and get the full member experience.

Join For Free

Linting and Its Importance

Q: Can linting make my code better?

A: No. If your logic is not good enough, it cannot help you, but it can surely make it look prettier.

Linting is the process of analyzing code to identify potential errors, code quality issues, and deviations from coding standards. It is a crucial part of modern software development for several reasons:

  • Error detection: Linting helps catch bugs and errors early in the development process.
  • Code quality: It enforces coding standards, making code more readable and maintainable.
  • Consistency: Ensures a uniform coding style across the codebase, which is particularly important in collaborative projects
  • Efficiency: Reduces the time spent on code reviews by automatically checking for common issues

Available Tools for Linting and Formatting

Several tools are available for linting and formatting Python code. Among them, the most popular are Black, Ruff, isort, PyLint, and Flake8, to name a few. There are unique strengths and weaknesses for each of the tools and they are also used for a specific purpose. In this article, we will look at Black, Ruff, and isort.

A Glorious Example of How Not to Code

Before diving into the comparison, let's take a look at a sample of poorly written Python code. This will help us illustrate the differences and capabilities of Black, Ruff, and isort.

Python
 
import datetime
from io import BytesIO
from datetime import datetime
from __future__ import unicode_literals
import os, sys, time
from base64 import b64encode
from PIL import Image, ImageDraw, Image
from flask import Flask, request, redirect, url_for, send_file
from werkzeug.utils import secure_filename

numbers = [1,
    2,
    4,5,6,
]

MyClass.function(arg1, arg2, arg3, flag, option)

def my_func(some_data: list, *args, path: os.PathLike, name: str, verbosity: bool = True, quiet: bool = False):
    """Processes `data` using `args` and saves to `path`."""
    with open(path, 'a') as file:
        ...



if first_condititon \
  and second_condition:
      ...


Black

Features

Black performs in-place code style changes with a prime focus on the following:

  • Opinionated (e.g., Spaces over Tabs) 
  • PEP8 Compliance [See Pragmatism] 
  • Smallest possible diff
  • Stability: Black has minimal to no configuration parameters, to ensure code style consistency.
  • Post-processing AST checks to ensure no change in logic. Optionally you can turn it off by using the –fast option.

Installation

Install Black by running this command:

 
pip install black


Example Usage

 
black [options] <SOURCE_FOLDER-or-FILE>


See black --help for more details.

How Did It Perform?

Python
 
import datetime
from io import BytesIO
from datetime import datetime
from __future__ import unicode_literals
import os, sys, time
from base64 import b64encode
from PIL import Image, ImageDraw, Image
from flask import Flask, request, redirect, url_for, send_file
from werkzeug.utils import secure_filename

numbers = [
    1,
    2,
    4,
    5,
    6,
]

MyClass.function(arg1, arg2, arg3, flag, option)


def my_func(
    some_data: list,
    *args,
    path: os.PathLike,
    name: str,
    verbosity: bool = True,
    quiet: bool = False
):
    """Processes `data` using `args` and saves to `path`."""
    with open(path, "a") as file:
        ...


if first_condititon and second_condition:
    ...


P.S. Notice how it did not sort/format the imports.

isort

Features

isort prioritizes import organization with a primary focus on:

  • Sorting: Sorts the imports alphabetically
  • Sections: Groups the imports into sections and by type
  • Multi-line imports: Arranges the multi-line imports into a balanced grid
  • Add/Remove imports: isort can be run or configured to add/remove imports automatically.

Installation

Install isort by running this command:

 
pip install isort


Example Usage

 
isort [OPTIONS] <SOURCE_FOLDER-or-FILE>


See isort --help for more details.

How Did It Perform?

Python
 
from __future__ import unicode_literals

import datetime
import os
import sys
import time
from base64 import b64encode
from datetime import datetime
from io import BytesIO

from flask import Flask, redirect, request, send_file, url_for
from PIL import Image, ImageDraw
from werkzeug.utils import secure_filename

numbers = [1,
    2,
    4,5,6,
]

MyClass.function(arg1, arg2, arg3, flag, option)

def my_func(some_data: list, *args, path: os.PathLike, name: str, verbosity: bool = True, quiet: bool = False):
    """Processes `data` using `args` and saves to `path`."""
    with open(path, 'a') as file:
        ...



if first_condititon \
  and second_condition:
      ...


P.S. Notice how the code was not formatted.

Ruff

Features

Ruff performs comprehensive linting and autofixes, adding type hints, and ensuring code quality and consistency.

  • Linting: Performs a wide range of linting checks
  • Autofix: Can automatically fix many issues
  • Integration: Easy to integrate with other tools such as isort
  • Configuration: Supports configuration via pyproject.toml or command-line flags.

Installation

Install Ruff by running this command:

 
pip install ruff


Example Usage

  • For linting:
 
ruff check [OPTIONS] <SOURCE_FOLDER-or-FILE>


  • For formatting:
 
ruff format [OPTIONS] <SOURCE_FOLDER-or-FILE>


See ruff --help for more details.

Note: Ruff does not automatically sort imports. In order to do this, run the following:

Shell
 
ruff check --select I --fix 

ruff format


How Did It Perform?

Python
 
from __future__ import unicode_literals

import datetime
import os
import sys
import time
from base64 import b64encode
from datetime import datetime
from io import BytesIO

from flask import Flask, redirect, request, send_file, url_for
from PIL import Image, ImageDraw
from werkzeug.utils import secure_filename

numbers = [
    1,
    2,
    4,
    5,
    6,
]

MyClass.function(arg1, arg2, arg3, flag, option)


def my_func(
    some_data: list,
    *args,
    path: os.PathLike,
    name: str,
    verbosity: bool = True,
    quiet: bool = False,
):
    """Processes `data` using `args` and saves to `path`."""
    with open(path, "a") as file:
        ...


if first_condititon and second_condition:
    ...


Where Do They Stand?


black

isort

ruff

Purpose

Code formatter

Import sorter and formatter

Linter and formatter

Speed

Fast

Fast

Extremely fast

Primary Functionality

Formats Python code to a consistent style

Sorts and formats Python imports

Lints Python code and applies autofixes

Configuration

pyproject.toml

pyproject.toml, .isort.cfg, setup.cfg

pyproject.toml or command-line flags

Ease of Use

High

High

High

Popularity

Very high

High

Increasing

Pros

Extensive, opinionated styling

Import grouping and sectioning for improved readability

Faster than most linters; developed on Rust

Cons

May not have extensive styling rules like pylint

-

Supports all F Rules from Flake8, although, Missing a majority of E rules

Conclusion

Black, Ruff, and isort are powerful tools that help maintain high code quality in Python projects. Each tool has its specific strengths, making them suitable for different aspects of code quality:

  • Black: Best for automatic code formatting and ensuring a consistent style
  • isort: Perfect for organizing and formatting import statements
  • Ruff: Ideal for comprehensive linting and fixing code quality issues quickly

By understanding the unique features and benefits of each tool, developers can choose the right combination to fit their workflow and improve the readability, maintainability, and overall quality of their codebase.

Tool code style Python (language) Lint (software)

Opinions expressed by DZone contributors are their own.

Related

  • An Overview of Creating Databases With Python
  • DocRaptor vs. WeasyPrint: A PDF Export Showdown
  • How to Create Your Own Cryptocurrency Blockchain in Python
  • Alexa Skill With Python

Partner Resources


Comments

ABOUT US

  • About DZone
  • Send feedback
  • Community research
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 100
  • Nashville, TN 37211
  • support@dzone.com

Let's be friends: