Aller au contenu

Bandit Python Sécurité Linter Cheat Sheet

Copier toutes les commandes Générer PDF

Aperçu général

Bandit est un linter de sécurité conçu pour trouver des problèmes de sécurité communs dans le code Python. Il analyse le code source Python et identifie les vulnérabilités potentielles en matière de sécurité en scannant les modèles connus et les anti-patterns. Bandit est largement utilisé dans les pipelines DevSecOps pour attraper les problèmes de sécurité au début du processus de développement, en faisant un outil essentiel pour le développement sécurisé de Python.

C'est pas vrai. Note : Bandit est conçu pour identifier les problèmes de sécurité potentiels et devrait être utilisé dans le cadre d'une stratégie globale d'essais de sécurité. Il peut produire de faux positifs et devrait être combiné avec d'autres méthodes de tests de sécurité.

Installation

Utilisation de pip

# Install Bandit
pip install bandit

# Install with additional formatters
pip install bandit[toml]

# Install development version
pip install git+https://github.com/PyCQA/bandit.git

# Verify installation
bandit --version

Utilisation de conda

# Install from conda-forge
conda install -c conda-forge bandit

# Create dedicated environment
conda create -n security-tools bandit
conda activate security-tools
```_

### Utilisation des gestionnaires de paquets
```bash
# Ubuntu/Debian
sudo apt update
sudo apt install bandit

# CentOS/RHEL/Fedora
sudo dnf install bandit
# or
sudo yum install bandit

# macOS with Homebrew
brew install bandit

# Arch Linux
sudo pacman -S bandit
```_

### Installation Docker
```bash
# Pull official Bandit image
docker pull securecodewarrior/bandit

# Run Bandit in container
docker run --rm -v $(pwd):/code securecodewarrior/bandit bandit -r /code

# Build custom image
cat > Dockerfile ``<< 'EOF'
FROM python:3.9-slim
RUN pip install bandit
WORKDIR /app
ENTRYPOINT ["bandit"]
EOF

docker build -t custom-bandit .
docker run --rm -v $(pwd):/app custom-bandit -r .

Utilisation de base

Analyses simples

# Scan a single file
bandit example.py

# Scan a directory recursively
bandit -r /path/to/project

# Scan current directory
bandit -r .

# Scan with verbose output
bandit -v -r .

# Scan specific files
bandit file1.py file2.py file3.py

# Scan with specific confidence level
bandit -r . -i  # Show only high confidence issues
bandit -r . -ii # Show medium and high confidence issues
bandit -r . -iii # Show all confidence levels

Formats de sortie

# JSON output
bandit -r . -f json

# XML output
bandit -r . -f xml

# CSV output
bandit -r . -f csv

# HTML output
bandit -r . -f html

# YAML output
bandit -r . -f yaml

# Custom output
bandit -r . -f custom --msg-template "\\\{abspath\\\}:\\\{line\\\}: \\\{test_id\\\}[bandit]: \\\{severity\\\}: \\\{msg\\\}"

# Save output to file
bandit -r . -f json -o bandit-report.json
bandit -r . -f html -o bandit-report.html

Gravité et filtrage de la confiance

# Filter by severity (LOW, MEDIUM, HIGH)
bandit -r . -l  # Low severity and above
bandit -r . -ll # Medium severity and above
bandit -r . -lll # High severity only

# Filter by confidence (LOW, MEDIUM, HIGH)
bandit -r . -i  # High confidence only
bandit -r . -ii # Medium and high confidence
bandit -r . -iii # All confidence levels

# Combine severity and confidence
bandit -r . -ll -ii # Medium+ severity, Medium+ confidence

Configuration

Fichier de configuration (.bandit)

# .bandit configuration file
tests: ['B201', 'B301']
skips: ['B101', 'B601']

exclude_dirs: ['*/tests/*', '*/venv/*', '*/env/*']

# Severity levels: LOW, MEDIUM, HIGH
severity: MEDIUM

# Confidence levels: LOW, MEDIUM, HIGH
confidence: MEDIUM

# Output format
format: json

# Include line numbers
include_line_numbers: true

# Aggregate results
aggregate: vuln

pyproject.toml Configuration

[tool.bandit]
exclude_dirs = ["tests", "venv", ".venv", "env", ".env"]
tests = ["B201", "B301"]
skips = ["B101", "B601"]

[tool.bandit.assert_used]
skips = ['*_test.py', '*test_*.py']

Configuration de la ligne de commande

# Exclude directories
bandit -r . --exclude /tests/,/venv/,/.venv/

# Skip specific tests
bandit -r . --skip B101,B601

# Run specific tests only
bandit -r . --tests B201,B301

# Exclude files by pattern
bandit -r . --exclude "*/migrations/*,*/settings/*"

# Include only specific file patterns
bandit -r . --include "*.py"

Utilisation avancée

Sélection de test personnalisé

# List all available tests
bandit -l

# Get detailed test information
bandit --help-tests

# Run specific vulnerability tests
bandit -r . --tests B101  # assert_used
bandit -r . --tests B102  # exec_used
bandit -r . --tests B103  # set_bad_file_permissions
bandit -r . --tests B104  # hardcoded_bind_all_interfaces
bandit -r . --tests B105  # hardcoded_password_string

# Skip specific tests
bandit -r . --skip B101,B102,B103

# Test categories
bandit -r . --tests B1*   # All B1xx tests
bandit -r . --tests B2*   # All B2xx tests
bandit -r . --tests B3*   # All B3xx tests

Données de référence et balayage progressif

# Create baseline
bandit -r . -f json -o baseline.json

# Compare against baseline
bandit -r . -f json|bandit-baseline -b baseline.json

# Progressive scanning (only new issues)
bandit -r . --baseline baseline.json

# Update baseline
bandit -r . -f json -o new-baseline.json

Intégration avec Git

__CODE_BLOCK_12_yaml

.github/flux de travail/sécurité.yml

nom : Scan de sécurité

le: [pousser, faire la demande]

emplois: Banditisme : course-on: ubuntu-latest étapes: - utilise: actions/checkout@v3

- nom : Configurer Python

utilise: actions/setup-python@v4 avec: python-version: «3,9»

- nom: Installer Bandit

exécuter: pip install bandit[toml]

- nom: Run Bandit

Run: bandit -r . -f json -o bandit-report.json

- nom : Télécharger les résultats

utilise: actions/upload-artifact@v3 avec: nom: rapport de banditisme chemin: bandit-report.json

- nom: Rapport Bandit

utilise: tj-actions/bandit@v5.1 avec: options: "-r . -f json" exit_zero & #160;: true __CODE_BLOCK_13_yaml

.gitlab-ci.yml

étapes: - sécurité

Banditisme : étape: sécurité image: python:3.9 avant_le_script : - pip installer bandit[toml] script & #160;: - -f json -o bandit-report.json artefacts : rapports: sast: bandit-report.json chemins: - Rapport de bandit.json expirer _dans : 1 semaine _failure d'autorisation : true

### Jenkins Pipeline
```groovy
// Jenkinsfile
pipeline \\ {
agent

étapes \\ {
étape('Scan de sécurité') \\ {
étapes \\{
script \\{
sh 'pip installer bandit[toml] '
-f json -o bandit-report.json '
\\}
\\}
après \\ {
toujours \\ {
archiveArtefacts artefacts: 'bandit-report.json', empreinte digitale: true
publierHTML([
permettre Faux.
toujoursLinkToLastBuild : true,
Tout garder: vrai,
rapport Dir: '.',
Dossiers: 'bandit-report.html',
nom du rapport: 'Rapport de sécurité de Bandit '
])
\\}
\\}
\\}
\\}
\\}
__CODE_BLOCK_15_yaml
# azure-pipélines.yml
déclencheur :
- principale

piscine:
vmImage: 'ubuntu-latest '

étapes:
- tâche : UsePythonVersion@0
Entrées:
version Spécifications: '3,9'

- script:
pip installer bandit[toml]
-json -o $(Agent.TempDirectory)/bandit-report.json
displayName: 'Run Bandit Security Scan '

- tâche: PublierTestRésultats@2
Entrées:
testResultsFiles: '$(Agent.TempDirectory)/bandit-report.json '
essai RunTitle: 'Scan de sécurité Bandit '

Common Vulnerability Patterns

Hardcoded Passwords (B105, B106, B107)

# BAD: Mot de passe codé dur
mot de passe = "secret123"
api_key = "abc123def456"

# BONNE : Variables environnementales
importations
mot de passe = os.environ.get('PASSWORD')
api_key = os.environ.get('API_KEY')

# Bon : fichier de configuration
importer configparser
config = configparser.ConfigParser()
config.read('config.ini')
mot de passe = config.get('database', 'password')

SQL Injection (B608)

# Formatage des chaînes
requête = "SELECT * FROM users WHERE id = %s" % user_id
requête = f"SELECT * FROM users WHERE id = \\{user_id\}"

# BON: Demandes paramétrées
curseur.execute("SELECT * FROM users WHERE id = %s", (user_id,))
curseur.execute("SELECT * FROM users Other id = ?", (user_id,))

Command Injection (B602, B605, B606, B607)

# BAT : injection de coquille
importations
os.system(f"ls \\{user_input\\}")
os.popen(f"grep \\{pattern\} \\{filename\\}")

# BON: Sous-processus avec liste
sous-processus d'importation
sous-processus.run(['ls', user_input])
sousprocess.run(['grep', pattern, filename])

Insecure Random (B311)

# DAU : aléatoire prévisible
importation aléatoire
jeton = aléatoire.randint(1000, 9999)

# BON: Cryptographiquement sécurisé
secrets d'importation
jeton = secrets.randen-dessous(9999)
secure_token = secrets.token_hex(16)

Unsafe YAML Loading (B506)

# BAD: Chargement de YAML sans danger
importation yaml
données = yaml.load(user_input)

# BON: Chargement sécurisé YAML
données = yaml.safe_load(user_input)
données = yaml.load(user_input, Loader=yaml.SafeLoader)

Custom Rules and Plugins

Creating Custom Tests

# _bandit_test.py personnalisé
importation bandit
de bandit. core import test_properties

@test_properties.test_id('B999')
@test_properties.checks('Appel')
def custom_security_check(context) :
"""Vérifier le modèle de sécurité personnalisé"""
if context.call_function_name_qual == 'dangerous_function' :
Revenez bandit. Numéro(
sévérité=bande. HAUT,
confiance=bandit. HAUT,
text="Utilisation de la fonction dangereuse détectée",
lineno=context.node.lineno,

Plugin Development

# Bande_plugin.py
de bandit. core import extension_loader

def load_tests():
"""Prendre des tests personnalisés"""
retour [custom_security_check]

# Enregistrez le plugin
extension_loader.MANAGER.register_plugin('custom_tests', load_tests)

Using Custom Tests

# Charger des tests personnalisés
--tests _bandit_test.py personnalisé

# Utiliser le plugin
bandit -r . --plugin bandit_plugin.py

Automation and Scripting

Automated Scanning Script

#!/usr/bin/env python3
# Bandit_scanner.py

sous-processus d'importation
Importation
importations
importation argparse
depuis l'importation de pathlib Voie

classe BanditScanner:
def __init__(self, project_path, config_file=Aucune):
auto.project_path = Chemin(projet_path)
self.config_file = fichier_config
Résultats personnels = \\{\\}

def run_scan(self, output_format='json', sévérité='MEDIUM', confiance='MEDIUM'):
"""Run Bandit scan avec les paramètres spécifiés"""
cmd = [
'bandit', '-r', str(self.project_path),
'-f', format de sortie,
f'-l\\{self._severity_to_flag(severity)\\}',
f'-i\\{self._confiance_to_flag(confiance)\\} '
- Oui.

si self.config_file :
cmd.extend(['--configfile', self.config_file])

Essayez :
result = subprocess.run(cmd, capture_output=True, text=True, check=False)

si sortie_format == 'json':
self.results = json.loads(result.stdout) si résultat. stdout autre \\{\\}
Sinon:
self.results = result.stdout

Return result.returncode == 0

sauf sous-processus. Processus appelé Erreur comme e:
print(f"Error running Bandit: \\{e\}")
Retour Faux
Sauf Json. JSONDécode Erreur comme e:
print(f"Error analyse la sortie JSON: \\{e\}")
Retour Faux

def _severity_to_flag(self, sévérité):
"""Convertir la sévérité au drapeau de Bandit"""
mapping = \\{'LOW': '', 'MEDIUM': 'l', 'HIGH': 'll'\\}
carte de retour. get(severity.upper(), 'l')

def _confiance_to_flag(self, confidence):
"""Convertir la confiance au drapeau de Bandit"""
mapping = \\{'LOW': 'ii', 'MEDIUM': 'i', 'HIGH': ''\\}
retour mapping.get(confiance.upper(), 'i')

def get_summary(self):
"""Get scan summit"""
Si ce n'est pas le cas (self.results, dict):
retour "Aucun résultat disponible"

métriques = auto.results.get('metrics', \\{\\})
retour \\{
'total_lines': métriques.get('_totals', \\{\\}).get('loc', 0),
«total_issues»: len(self.results.get('results', []),
'high_severity': len([r pour r dans self.results.get('results', [])
si r.get('issue_sévérité') == 'HIGH']),
'medium_severity': len([r pour r dans self.results.get('results', [])
si r.get('issue_sévérité') == 'MEDIUM']),
'low_severity': len([r pour r dans self.results.get('results', [])
si r.get('issue_severity') == 'LOW'])
\\}

def get_issues_by_severity(self, sévérité='HIGH'):
"""Obtenez les problèmes filtrés par la gravité"""
Si ce n'est pas le cas (self.results, dict):
retour []

retour [émission dans self.results.get('results', [])
if issue.get('issue_sévérité') == sévérité.upper()]

def generate_report(self, output_file='bandit_report.html'):
"""Générer le rapport HTML"""
cmd = [
'bandit', '-r', str(self.project_path),
'-f', 'html', '-o', fichier_sortie
- Oui.

si self.config_file :
cmd.extend(['--configfile', self.config_file])

Essayez :
sousprocessus.run(cmd, check=True)
retour Vrai
sauf sous-processus. Processus appelé Erreur :
Retour Faux

def save_results(self, output_file='bandit_results.json'):
"""Enregistrer les résultats dans le fichier"""
si l'institution (self.results, dict):
avec open(output_file, 'w') comme f:
json.dump(self.results, f, tiret=2)
Sinon:
avec open(output_file, 'w') comme f:
f.write(str(self.results))

def main():
parser = argparse. ArgumentParser(description='Scanner automatique de bande')
parser.add_argument('project_path', help='Path to projet to scan')
parser.add_argument('--config', help='Bandit fichier de configuration')
parser.add_argument('--sévérité', par défaut='MEDIUM',
choix=['LOW', 'MEDIUM', 'HIGH'],
help='Niveau minimal de gravité')
parser.add_argument('--confiance', par défaut='MEDIUM',
choix=['LOW', 'MEDIUM', 'HIGH'],
help='Niveau de confiance minimal')
parser.add_argument('--output', help='Output file for results')
parser.add_argument('--report', help='Generate HTML report')

args = parser.parse_args()

scanner = BanditScanner(args.project_path, args.config)

print(f"Scanning \\{args.project_path\\}...")
succès = scanner.run_scan(sévérité=args.sévérité, confiance=args.confiance)

si succès:
résumé = scanner.get_sommary()
print(f"Scan terminé avec succès!")
print(f"Toutes les lignes du code: \\{sommary['total_lines']\\}")
print(f"Total des numéros trouvés : \\{sommary['total_issues']\\}")
print(f"Haute sévérité: \\{résumé['haute_sévérité']\\}")
print(f"Moyenne de gravité: \\{résumé['medium_severity']\\}")
print(f"Faible sévérité: \\{sommary['low_severity']\\}")

en cas d'args. sortie & #160;:
Scanner.save_results(args.output)
print(f"Résultats enregistrés dans \\{args.output\\}")

si args.rapport:
si scanner.generate_report(args.report):
print(f"Rapport HTML généré: \\{args.report\\}")
Sinon:
print("Echec de générer un rapport HTML")

        # Exit with error code if high severity issues found
si résumé['haute_séquence''] >`` 0:
print("Questions de grande gravité trouvées!")
sys.exit(1)
Sinon:
print("Scan a échoué!")
sys.exit(1)

Si _nom____ «__main__»:
principal()

Batch Processing Script

#!/bin/bash
# batch_bandit_scan.sh

# Configuration
PROJETS_DIR=/chemin/vers/projets"
RAPPORTS_DIR--/chemin/à/rapports"
DATE=$(date +%Y%m%d_%H%M%S)

# Créer un répertoire de rapports
Mkdir -p "$REPORTS_DIR"

# Fonction pour scanner le projet
scan_projet() \{
projet local_path=1$"
nom_projet local=$(nom de base "$project_path")
Rapport local_fichier=$REPORTS_DIR/$\{projet_name\}_$\{DATE\}.json"
rapport_html local$ RAPPORTS_DIR/$\{project_name\}_$\{DATE\}.html"

écho "Scanning $project_name..."

    # Run Bandit scan
bandit -r "$project_path" -f json -o "$report_file" -ll -ii
bandit -r "$project_path" -f html -o "$html_report" -ll -ii

    # Check for high severity issues
high_issues=$(jq '.results="map(select(.issue_severity == "HIGH"))"longueur" "$report_file")

si [ "$high_issues" -gt 0 ];
echo "WARNING: $project_name a $high_issues high sévérité issues!"
echo "$project_name" >> "$REPORTS_DIR/high_severity_projects.txt"
Fi

echo "Scan terminé pour $project_name"
\}

# Scanner tous les projets Python
trouver "$PROJECTS_DIR" -nom "*.py" -type f=lors de la lecture -r fichier; faire
project_dir=$(dirname "$file")
si [ ! -f "$project_dir/.bandit_scanned" ];
scan_projet "$project_dir"
touche "$project_dir/.bandit_scanned"
Fi
Fait

echo "Scannage par lots terminé. Rapports enregistrés dans $REPORTS_DIR"

Integration with IDEs

VS Code Integration

// .vscode/settings.json
\ {
"python.linting.banditEnabled" : vrai,
"python.linting.banditArgs": [
"--niveau de gravité", "moyen",
"--niveau de confiance", "moyen"
Les
"python.linting.enabled": vrai
\}

PyCharm Integration

# Configuration de l'outil externe
# Programme : banditisme
# Arguments : -r $FileDir$ -f json
# Répertoire de travail : $ProjectFileDir$

Vim/Neovim Integration

" .vimrc ou init.vim
" Intégration Bandit avec ALE
g:ale_linters = \{
\ 'python': ['bandit', 'flake8', 'pylin'],
\\}

g:ale_python_bandit_options = '-ll -ii '

Best Practices

Configuration Management

# .bandit - Configuration complète
'B60', 'B105', 'B106', 'B107', 'B108', 'B110', 'B112', 'B201', 'B301', 'B302', 'B303', 'B304', 'B304', 'B315', 'B307', 'B308', 'B309', 'B310', 'B311', 'B312', 'B313', 'B314', 'B315', 'B316', 'B317', 'B318', 'B319', 'B320', 'B322', 'B323', 'B323', 'B324', 'B325', 'B401', 'B402', 'B404', 'B404', 'B402', 'B405', 'B60', 'B60', 'B50', 'B4', 'B4

skips : ['B101'] # Sauter asserment_utilisé dans les fichiers test

_dirs exclus : [
«*/tests/*»,
«*/essai/*»,
«*/.venv/*»,
«*/venv/*»,
«*/.env/*»,
«*/env/*»,
«*/migrations/*»,
«*/node_modules/*»,
"*/.git/*"
- Oui.

# Gravité: faible, moyenne, élevée
gravité: MOYEN

# Confiance: faible, moyenne, élevée
confiance: MOYEN

False Positive Management

# Commentaires en ligne pour supprimer les avertissements
mot de passe = "par défaut" # nezec B105

# Suppression de l'essai spécifique
sous-processus d'importation
sous-processus.call(shell_command, shell=True) # nezc B602

# Suppression des essais multiples
eval(user_input) Nezc B307,B102

Team Workflow Integration

# Configuration pré-commit (.pre-commit-config.yaml)
Repos:
  - Date de naissance:
rev: '1.7.5'
crochets:
      - id: banditisme
['-ll', '-ii']
hors: ^tests/

# Faire l'intégration de fichier
. PHONIE: Scan de sécurité
sécurité-scan:
-i -f json -o rapport de sécurité.json
@echo "Scan de sécurité terminé. Vérifiez les résultats de security-report.json."

. Contrôle de sécurité
contrôle de sécurité:
-ii
@si [ $? -ne 0 ]; puis \
echo « Problèmes de sécurité trouvés. Veuillez examiner et corriger."; \
sortie 1; \
Fi

Troubleshooting

Common Issues

# Question: ImportError lors de l'exécution de Bandit
# Solution : Assurer un environnement Python approprié
python -m pip install --upgrade bandit

# Question : La configuration n'est pas lue
# Solution: Vérifier l'emplacement et la syntaxe des fichiers de configuration
bandit --aide-config

# Question : Trop de faux positifs
# Solution: Configuration des tunes et suppressions d'utilisation
bandit --skip B101,B601 -ll -ii

# Question : Problèmes de rendement avec les grandes bases de codes
# Solution: Exclure les répertoires inutiles
--à l'exclusion de "*/venv/*,*/node_modules/*,*/.git/*"

# Question: L'intégration avec l'IC/CD échoue
# Solution: Utiliser les codes de sortie appropriés et le traitement des erreurs
Banditisme -r . -ll -ii- # Continuer sur les erreurs

Performance Optimization

# Traitement parallèle (le cas échéant)
Le bandit-r. --processus 4

# Exclure les grands répertoires
--exclut "*/venv/*,*/env/*,*/node_modules/*,*/.git/*,*/migrations/*"

# Utiliser uniquement des tests spécifiques
Le banditisme. --essais B201,B301,B401,B501

# Limiter la profondeur de récursion
trouver . -nom "*.py" -pas -chemin "*/venv/*"

Debugging

# Sortie verbale
Le banditisme -v -r .

# Mode débogage
- d -r .

# Afficher les fichiers supprimés
Le bandit-r. --verbose

# Tester le fichier spécifique avec tous les détails
bandit -v -ll -iii specific_file.py

Resources


This cheat sheet provides comprehensive guidance for using Bandit to identify security vulnerabilities in Python code. Always combine static analysis with other security testing methods for comprehensive coverage.

|xargs bandit -ll -ii

## Intégration CI/CD

### Actions GitHub

GitLab CI

### GitLab CI

Jenkins Pipeline

### Jenkins Pipeline

Azure DevOps

### Azure DevOps

Common Vulnerability Patterns

Hardcoded Passwords (B105, B106, B107)

## Vulnérabilité Modèles

### Mot de passe à code dur (B105, B106, B107)

SQL Injection (B608)

### Injection SQL (B608)

Command Injection (B602, B605, B606, B607)

### Injection de commandement (B602, B605, B606, B607)

Insecure Random (B311)

### Aléatoire incertain (B311)

Unsafe YAML Loading (B506)

### Chargement de YAML non sûr (B506)

Custom Rules and Plugins

Creating Custom Tests

## Règles et plugins personnalisés

### Création de tests personnalisés

Plugin Development

### Développement de plugins

Using Custom Tests

### Utilisation de tests personnalisés

Automation and Scripting

Automated Scanning Script

## Automatisation et écriture

### Scénario de numérisation automatisé

Batch Processing Script

### Script de traitement par lots

Integration with IDEs

VS Code Integration

## Intégration avec les IDE

### Intégration du code VS

PyCharm Integration

### Intégration PyCharm

Vim/Neovim Integration

### Intégration Vim/Neovim

Best Practices

Configuration Management

## Meilleures pratiques

### Gestion de la configuration

False Positive Management

### Gestion faussement positive

Team Workflow Integration

### Intégration des flux de travail en équipe

Troubleshooting

Common Issues

## Dépannage

### Questions communes

Performance Optimization

### Optimisation des performances

Debugging

### Déboguement

Resources


This cheat sheet provides comprehensive guidance for using Bandit to identify security vulnerabilities in Python code. Always combine static analysis with other security testing methods for comprehensive coverage.

|xargs bandit -ll -ii ```

Ressources

  • [Documentation officielle de Bandit] (LINK_6)
  • [Résistoire Bandit GitHub] (LINK_6)
  • [Python, pratiques exemplaires en matière de sécurité] (LINK_6)
  • [Sécurité des Pythons de l'OWASP] (LINK_6)
  • [Outils PyCQA] (LINK_6)

*Cette feuille de triche fournit des conseils complets pour l'utilisation de Bandit pour identifier les vulnérabilités de sécurité dans le code Python. Toujours combiner l'analyse statique avec d'autres méthodes de tests de sécurité pour une couverture complète. *