Python security, static analysis, and AI code review that developers can actually use
Implementation guides, incident-style research, and CI workflows for Python teams that want lower-noise AppSec and better AI-generated code review.
Articles across Python security, AI code risk, dead code, CI hardening, and workflow changes.
Curated discovery paths so readers can scan by job-to-be-done instead of publish date.
Guides, case studies, comparisons, and research pieces with clear next steps.
Article library
Showing all blog articles
Search the library, choose one of the three common topics, or open More filters.
More filtersTopics, formats, and frameworks
Topic
Format
Framework
Featured article
Start with this article
Testwashing: When Coding Agents Delete Tests to Pass CI
Coding agents sometimes delete, skip or rig a failing test so CI goes green. We tried 9 versions: pytest passed every one. Here's what catches each.
Why this is worth your time
Useful if coding agents fix failing tests in your repository and you want to know whether the code was fixed or the test was.
Testwashing is when a coding agent deletes, skips or weakens a test so CI goes green, then reports the work as done. It's a form of reward hacking that Anthropic, METR and the ImpossibleBench authors have documented.
In our test, pytest reported green for all nine versions. `skylos done` failed the deleted test, the skipped test, the emptied assertion, the `--deselect` setting, the hard-coded answer and the `__eq__` that always returns True.
It missed three: a deleted test with a new test added in its place, an assertion loosened to a truthiness check, and an expected value edited to match the bug. Read every change to a test file.
Library
Keep exploring
Does SonarQube Detect Dead Code? What Its Rules Cover in 2026
SonarQube reports unused code that's local or private: variables, parameters, assignments, imports, private methods, fields and classes, and unreachable statements.
What you'll get
Useful if you rely on SonarQube and want to know which kinds of dead code it reports and which it can't see.
How to Find Dead Code in TypeScript: Unused Exports, Classes and Files
`tsc --noUnusedLocals` and ESLint's `no-unused-vars` find unused locals and imports inside one file. They can't tell whether an export is used by another file.
What you'll get
Useful if your TypeScript codebase has grown and you want to find exports, classes and whole files that nothing uses anymore.
"All Tests Pass": What One Free Scan Found in an AI-Style Pull Request
In our test, pytest reported "2 passed" after a test was deleted. `skylos done` failed the change and named the deleted test.
What you'll get
Useful if coding agents write part of your code and you want to see what a free, local scan catches before you merge.
A SonarQube-Style PR Gate in GitHub Actions, With No Server
SonarQube's own pull request checks need SonarQube Cloud or Developer Edition and up of SonarQube Server.
What you'll get
Useful if you want SonarQube-style quality gates on pull requests but don't want to run a SonarQube server or pay per line of code.
SonarQube Community Build Pull Request Analysis (2026)
SonarQube Community Build doesn't analyze pull requests or feature branches; Sonar starts both in Developer Edition.
What you'll get
Useful if you run SonarQube Community Build and want pull requests checked before merge without moving to a paid edition.
SonarQube Pricing (2026): Cloud, Server and Free Plans
SonarQube is priced by lines of code: SonarQube Cloud's Team plan starts at about $34 a month for up to 100k lines, and Server editions are priced per instance, per year.
What you'll get
Useful if you're budgeting for SonarQube, outgrowing its free tier, or comparing it with free alternatives.
Your AI Agent Just Tried to Install a Package That Doesn't Exist
Models sometimes invent package names. A study of 576,000 generated code samples found 205,474 unique made-up package names (Spracklen et al., USENIX Security 2025).
What you'll get
Useful if Claude Code, Cursor or Codex can run install commands in your repo and you want made-up or typosquatted packages stopped before they download.
Vulture False Positives: Tested Configs for Flask, Django and pytest
Vulture reports code the framework calls (routes, signal receivers, admin hooks, fixtures) as unused, because nothing in your code calls it.
What you'll get
Copy-paste Vulture configs for Flask, Django and pytest, each tested on a sample app with the before and after output.
Is There a Knip for Python? Unused Code, Files and Deps
There is no Python tool with Knip's maturity yet. The closest in scope is chokkin, which calls itself 'a Knip-like experience for Python': unused files, dependencies and public symbols. It was first released in June 2026.
What you'll get
A check-by-check map from Knip to Python tools (chokkin, Vulture, deptry, Skylos), with real output from one test project.
Does Ruff Detect Dead Code? What It Finds and What It Misses
Ruff detects dead code only inside one file: unused imports (F401), unused local variables (F841), names redefined while unused (F811), unused arguments (ARG001–ARG005) and a few more.
What you'll get
A direct answer to whether Ruff finds dead code, with tested output on a three-file example and a Flask app, and a working Ruff plus Skylos pre-commit config.
GitHub Actions PR Gate for AI-Generated Code: A Practical Security Workflow
A safe AI-generated-code PR gate should run on pull_request with least-privilege permissions, not a privileged pull_request_target workflow that checks out untrusted code.
What you'll get
Useful if your team already lets Claude Code, Cursor, Copilot, Codex, or other agents produce pull requests and needs a concrete GitHub Actions gate instead of a generic AI security checklist.
Next.js SaaS Security Checklist: 9 Bugs We Fixed Before They Became Incidents
The dangerous SaaS bugs were not only in business logic. They appeared at boundaries: analytics, RLS, RPCs, billing refunds, public quotas, share tokens, and uploaded metadata.
What you'll get
Useful for teams building a Next.js and Supabase SaaS who want practical security checks around RLS, billing entitlements, analytics, public routes, and AI-assisted code review.
AI Coding Agent Security Checklist: 12 Controls Before Agents Open PRs
AI coding agent security is different from AI autocomplete security because agents can take actions: edit files, run commands, install packages, call tools, and produce PRs.
What you'll get
Useful if your team has moved from AI autocomplete to AI coding agents and needs concrete guardrails before those agents touch production repos.
GitHub Actions Security and GitLab CI Security: Static Analysis for CI/CD
CI/CD YAML should be reviewed like privileged code because it controls tokens, secrets, artifacts, release jobs, and deployment paths.
What you'll get
Use this if you want to treat CI/CD workflow files like privileged code and catch high-risk GitHub Actions or GitLab CI patterns before merge.
Is AI-Generated Python Code Insecure in 2026? What the Research Shows
Veracode's July 2026 report puts the average security pass rate at 56% across more than 100 models, essentially unchanged from the year before. 44% of tested generation tasks failed at least one covered check.
What you'll get
A careful reading of current AI code security research, with the benchmark limits and practical Python controls stated plainly.
AI Code Review for Security: A PR Checklist for Auth, Tenant Isolation, Validation, and Secrets
AI code review security should check both newly introduced vulnerabilities and security controls that disappeared from the diff.
What you'll get
Useful if your team uses Cursor, Claude Code, Copilot, Codex, or other AI coding tools and needs a practical PR security checklist instead of another generic AI security overview.
We Tested Dead-Code Detection by Sending Cleanup PRs to Mature OSS Repos
The useful test for dead-code detection is not whether a scanner prints findings; it is whether maintainers accept the cleanup.
What you'll get
A proof-led explanation of dead-code false positives, maintainer review, and the difference between benchmark signal and real cleanup work.
Best AI Code Security Tools in 2026 Compared
The market is mixing together three different jobs: AI review assistance, traditional SAST, and AI-specific regression detection.
What you'll get
Useful if you are trying to choose the right security workflow for AI-generated code instead of buying the loudest new category label.
Flask Security Scanning: What Static Analysis Actually Catches in 2026
Flask security issues rarely come from Flask itself. They come from the raw Python and library calls Flask apps make around requests, templates, files, and subprocesses.
What you'll get
This completes the Django / FastAPI / Flask framework cluster and gives Python teams a cleaner way to evaluate scanner coverage by framework.
Slopsquatting in Python: How Hallucinated Package Names Become Attacks
Slopsquatting: registering a package name AI models invent, so whoever pip installs it runs the attacker's code. What the research found and how to catch it.
What you'll get
A Python-focused read of the package-hallucination research, with the numbers checked against the paper's coverage and a working way to block hallucinated installs.
python.linting Is Deprecated in VS Code: What Python Teams Should Use Now
The old `python.linting.*` settings are deprecated; VS Code now expects dedicated tool extensions.
What you'll get
High-intent migration query with a direct path from editor setup into security scanning.
FastAPI Security Scanning: 8 Vulnerability Patterns Static Analysis Catches
Pydantic validates shape, not intent. Eight FastAPI vulnerability patterns, from SSRF to unsafe uploads, and which scanners catch each one.
What you'll get
Use this if your team ships async Python APIs and wants concrete FastAPI vulnerability patterns, not generic SAST advice.
Django Security Scanning: What Static Analysis Actually Catches in 2026
Django's ORM blocks SQL injection until code uses raw(), .extra() or cursor.execute(). Seven Django vulnerability patterns and which scanners catch each.
What you'll get
The Django guide is the clearest framework-specific entry point for teams comparing Python security scanners.
Best Python Static Analysis Tools Compared: Bandit vs Vulture vs Skylos (2026)
A side-by-side comparison of Python static analysis tools for security, dead code, framework awareness, speed, and CI/CD integration.
What you'll get
This is the fastest way to understand where Bandit, Vulture, and Skylos differ before you install anything.
Dead Code in Python Isn't Just Tech Debt — It's a Security Liability
Dead code is a security risk when it is still deployed: old routes nobody patches, unused dependencies with CVEs, stale credentials. How to find and remove it.
What you'll get
Start here if you want the strategic reason dead code belongs in an AppSec workflow, not just a cleanup backlog.
How AI-Generated PRs Are Overwhelming Code Review (and How to Fix It)
AI writes code faster than teams can review it. Why the AI PR flood is breaking code review, and how to automate security and quality gates.
What you'll get
Good starting point if your team’s problem is review overload, not just individual vulnerabilities.
Vibe Coding Security Checklist for Python Apps (With the Checks to Run)
Most security bugs in vibe-coded Python apps are old ones: secrets in code, string-built SQL, shell commands with user input, user input as a template, disabled TLS, debug mode on.
What you'll get
A Python-specific, code-level checklist for apps built with AI assistants, where every item says how to check it and what a scanner did and didn't flag on a real vibe-coded file.
Why Python SAST Tools Drown Teams in False Positives (and What Actually Works)
Why SAST tools get noisy, and the controls that keep Python security findings trustworthy: taint tracking, baselines, diff scans and reviewed suppressions.
What you'll get
Best read for teams trying to understand why SAST noise happens before they compare tools.