A comprehensive Python code quality checking tool that wraps PyFlakes, pycodestyle, and McCabe to provide unified static analysis with extensible plugin support.
—
Command-line entry point and application management for running flake8 as a standalone tool or integrating it into scripts and build systems.
Execute flake8 from Python code with full command-line argument support.
from collections.abc import Sequence
def main(argv: Sequence[str] | None = None) -> int:
"""
Main entry point for flake8 command-line execution.
Creates an Application instance, runs the complete flake8 workflow
(argument parsing, file discovery, checking, reporting), and returns
the appropriate exit code.
Parameters:
argv: Command-line arguments to process. If None, uses sys.argv[1:]
Arguments follow standard flake8 CLI format:
- File/directory paths to check
- Configuration options (--max-line-length, --ignore, etc.)
- Output options (--format, --output-file, --statistics, etc.)
Returns:
int: Exit code indicating success (0) or failure (>0)
- 0: No violations found
- >0: Number of violations found (or general error)
Example:
# Check specific files with custom options
exit_code = main(['--max-line-length=88', '--ignore=E203,W503', 'myapp/'])
# Check with statistics output
exit_code = main(['--statistics', '--show-source', 'project/'])
"""Usage example:
from flake8.main import cli
import sys
# Run flake8 on current directory with custom settings
exit_code = cli.main([
'--max-line-length=88',
'--ignore=E203,W503',
'--exclude=migrations,venv',
'--statistics',
'.'
])
# Exit with flake8's exit code
sys.exit(exit_code)Core application class for advanced integration and custom flake8 workflows.
class Application:
"""
Core application class that orchestrates flake8 execution.
Manages the complete flake8 workflow including plugin loading,
option parsing, file discovery, checking execution, and result reporting.
"""
def __init__(self) -> None:
"""Initialize a new Application instance."""
def run(self, argv: list[str]) -> None:
"""
Execute the complete flake8 workflow.
Parameters:
argv: Command-line arguments to process
"""
def exit_code(self) -> int:
"""
Get the exit code after running flake8.
Returns:
int: Exit code based on execution results
- 0: Success, no violations
- >0: Violations found or error occurred
"""
@property
def result_count(self) -> int:
"""
Number of violations found after execution.
Returns:
int: Total count of errors and warnings found
"""
@property
def start_time(self) -> float:
"""Timestamp when Application was instantiated."""
@property
def end_time(self) -> float | None:
"""Timestamp when Application finished, or None if still running."""Usage example:
from flake8.main.application import Application
# Create and run application manually
app = Application()
app.run(['--show-source', 'myproject/'])
# Check results
if app.result_count > 0:
print(f"Found {app.result_count} violations")
exit_code = app.exit_code()
else:
print("No violations found!")
exit_code = 0
# Calculate execution time
if app.end_time:
duration = app.end_time - app.start_time
print(f"Execution took {duration:.2f} seconds")When using the main() function or Application.run(), flake8 accepts standard command-line arguments:
--exclude: Comma-separated patterns to exclude--filename: Patterns for files to include--stdin-display-name: Display name when reading from stdin--select: Comma-separated error codes to check for--ignore: Comma-separated error codes to ignore--extend-ignore: Additional error codes to ignore--per-file-ignores: File-specific ignores--format: Output format string--output-file: Write output to file--show-source: Show source code for each error--statistics: Show violation statistics--count: Show total error count--quiet: Reduce output verbosity--config: Path to configuration file--max-line-length: Maximum line length--max-complexity: Maximum cyclomatic complexity--jobs: Number of parallel jobs#!/usr/bin/env python3
"""Code quality check script."""
from flake8.main import cli
import sys
import os
def main():
"""Run flake8 with project-specific configuration."""
# Define project-specific settings
flake8_args = [
'--max-line-length=88',
'--ignore=E203,W503,E501',
'--exclude=migrations,venv,.git,__pycache__',
'--statistics',
'--show-source',
]
# Add target directories
target_dirs = ['src/', 'tests/']
for directory in target_dirs:
if os.path.exists(directory):
flake8_args.append(directory)
# Run flake8
print("Running flake8 code quality checks...")
exit_code = cli.main(flake8_args)
if exit_code == 0:
print("✅ All code quality checks passed!")
else:
print("❌ Code quality issues found!")
return exit_code
if __name__ == "__main__":
sys.exit(main())#!/usr/bin/env python3
"""Git pre-commit hook using flake8."""
from flake8.main import cli
import subprocess
import sys
def get_staged_python_files():
"""Get list of staged Python files."""
result = subprocess.run(
['git', 'diff', '--cached', '--name-only', '--diff-filter=ACM'],
capture_output=True, text=True
)
files = result.stdout.strip().split('\n')
python_files = [f for f in files if f.endswith('.py') and f]
return python_files
def main():
"""Run flake8 on staged files."""
staged_files = get_staged_python_files()
if not staged_files:
print("No Python files staged for commit.")
return 0
print(f"Checking {len(staged_files)} staged Python files...")
# Run flake8 on staged files only
flake8_args = [
'--max-line-length=88',
'--ignore=E203,W503',
'--show-source'
] + staged_files
exit_code = cli.main(flake8_args)
if exit_code != 0:
print("❌ Flake8 found issues in staged files.")
print("Fix the issues or use 'git commit --no-verify' to bypass.")
return exit_code
if __name__ == "__main__":
sys.exit(main())"""Build system integration example."""
from flake8.main.application import Application
import time
class BuildStep:
"""Flake8 build step for CI/CD integration."""
def __init__(self, config=None):
self.config = config or {}
def run_quality_check(self, source_dirs):
"""Run flake8 as part of build process."""
print("Starting code quality check...")
start_time = time.time()
# Configure flake8 arguments
args = [
'--statistics',
'--format=%(path)s:%(row)d:%(col)d: %(code)s %(text)s',
'--output-file=flake8-report.txt'
]
# Add configuration
if 'max_line_length' in self.config:
args.append(f"--max-line-length={self.config['max_line_length']}")
if 'ignore' in self.config:
args.append(f"--ignore={','.join(self.config['ignore'])}")
# Add source directories
args.extend(source_dirs)
# Run application
app = Application()
app.run(args)
# Report results
duration = time.time() - start_time
print(f"Quality check completed in {duration:.2f}s")
print(f"Found {app.result_count} violations")
return app.exit_code() == 0
# Usage in build script
build_step = BuildStep({
'max_line_length': 88,
'ignore': ['E203', 'W503']
})
success = build_step.run_quality_check(['src/', 'tests/'])
if not success:
print("Build failed due to code quality issues")
exit(1)Install with Tessl CLI
npx tessl i tessl/pypi-flake8