
Begin
14 pages · ~28 min
Python Code Quality Assessment
This training teaches developers to assess and improve the quality of Python code, covering best practices for writing clean, maintainable, and reliable programs.
A digital instructor presents all 14 pages. Hold “Ask” at any point and ask out loud — the answer comes from this course. No sign-up needed.
What you’ll learn
- 01Evaluating the Quality of Python Programming: Course OverviewWelcome. This course is about evaluating the quality of Python programming, and its goal is practical: give you defensible criteria you can apply the next time you open a pull request or audit a codebase. Quality matters because it drives four things you already track: maintainability, the cost of defects, review throughput, and how fast new engineers onboard. We will work with six practical dimensions: correctness, readability, maintainability, testability, performance, and security. Each asks a different question about the same code. Then we focus on what is Python-specific: dynamic typing, idiomatic style, packaging, and dependency hygiene. From there, the roadmap moves through standards and tooling, review practice, measurement, technical debt, scaling, and a capstone audit. Whether you are a developer, a reviewer, a tech lead, a teacher, or an advanced learner, pick the track that fits your role. As a first check, look at your own repository and ask which of those six dimensions you can currently measure without guessing. Next, what quality actually means, through a reference model.
sonarsource.comaugmentcode.comkodus.io+22 min - 02What 'Quality' Means: A Reference ModelBefore we judge code, we need a reference model for what quality means. ISO/IEC 25010:2023 defines nine product quality characteristics. The ones that matter most in review are functional suitability, reliability, security, maintainability, flexibility, and safety. Map those down to the code itself: readability, analysability, modifiability, and testability. From a practitioner's view, six dimensions cover your review work: readability, maintainability, reliability, security, testability, and performance. Take a moment to check one function in your own codebase against all six. Here is the key point. Quality is trade-offs, not one number. A cache that speeds up hot paths can make state harder to reason about; strict typing improves analysability but adds ceremony. Dynamic typing makes this sharper, because you cannot lean on the compiler to catch mismatches. You need multiple signals: type hints and mypy strict, test coverage, complexity and duplication metrics, and human review. Next, How Quality Defects Show Up in Python Code.
iso.orgsis.seknowledge.bsigroup.com+22 min - 03How Quality Defects Show Up in Python CodeNow let's look at how quality defects actually surface in Python code. Start with the classic traps. Default values are evaluated once, at definition time, so a mutable default like an empty list is shared across every call. Use None and build the value inside the body. Closures capture the variable, not its value, so lambdas created in a loop all see the final value. Bind it with a default parameter. And reserve is for singletons like None. Use double equals for value comparison. Next, a bare except swallows KeyboardInterrupt and SystemExit. Catch the exception types you can recover from, and use raise from error to preserve the cause. Module-level mutable state creates hidden coupling, so tests pass alone and fail together. Then boundary failures. Check empty inputs, None in non-optional code, float equality, and assumed non-empty collections. For detection, Ruff E722 catches bare except. Ruff B006 catches mutable defaults, but it is opt-in, so select the B ruleset. Pylint W0102 flags dangerous defaults. Run those checks over your own code before review. Next, we move into correctness, reliability, and readability.
google.github.iodocs.quantifiedcode.comgithub.com+22 min - 04Correctness, Reliability, and ReadabilityLet's move on to correctness, reliability, and readability, the criteria you apply first in any review. Correctness starts with specific exception types, never a bare except, and context managers for files, connections, and locks. Keep try-block scope minimal and behavior deterministic rather than assuming the happy path. Here's the review question: does this except clause name exactly what it handles? For readability, require descriptive names, single-responsibility functions, shallow nesting, and no magic numbers. A literal like 5000 becomes a named constant that explains intent. For structure, keep __init__ light, use dataclasses for pure data, hold clear boundaries, and keep public interfaces backward compatible. Treat heuristics as signals: cyclomatic complexity at or below ten, functions around forty to sixty lines. The runtime raises the bar too. Python 3.15 arrives in October 2026, and Python 3.10 reached end of life on October 1, 2026. Run this checklist against your own code, then continue to security and dependency hygiene.
sonarsource.comaugmentcode.comkodus.io+22 min - 05Security and Dependency HygieneLet's move to security and dependency hygiene. Treat these as must-fix in every review. Use parameterized SQL, never build queries with string concatenation. No subprocess with shell set to true, and no unsafe deserialization on untrusted data, so avoid pickle loads and yaml load. Run Bandit, or Ruff's S rules, to catch these patterns early. For secrets, nothing hardcoded. Pull credentials from environment variables or a secrets manager, and commit a detect-secrets baseline so new leaks fail the build. On crypto, no MD5 or SHA1 for passwords, use the secrets module instead of random, never set verify to false, and parse XML with defusedxml. For dependencies, run pip-audit against your lockfile in CI, and block merges on high or critical CVEs. Finally, prioritize: static analysis on your code plus reachability-aware scanning on dependencies gives you one ranked queue. So before you merge, ask: does this diff introduce an unsafe pattern, a secret, or an unpatched dependency? Next, we turn to Pythonic style: PEP 8, PEP 20, and project conventions.
awesomepython.devsafeguard.shdiffchecker.pro+22 min - 06Pythonic Style: PEP 8, PEP 20, and Project ConventionsNext, Pythonic style. PEP 8 gives you a consistency hierarchy. Consistency with the guide matters, consistency within a project matters more, and consistency within a module or function matters most. So when you review, ask which level the deviation violates. Deviate deliberately for readability, for surrounding code, or for legacy modules you are not otherwise touching.
Use the Zen of Python as a design filter. If a function needs a paragraph to justify its shape, it probably fails readability counts. PEP 257 governs docstrings, so public modules, classes, and functions get real summaries.
Automate what is mechanical. Black and Ruff format default to eighty-eight characters, about ten percent over seventy-nine, and since Black owns the slice spacing, add E203 to your ignore list rather than fight it. Keep those settings in pyproject dot toml so every machine and continuous integration run agrees. Ruff's I rules sort three import groups: standard library, third-party, then local, separated by blank lines. Apply that check to one file you own today. Now let's look at static analysis and automated quality gates.
google.github.iodocs.quantifiedcode.comgithub.com+22 min - 07Static Analysis and Automated Quality GatesNext, let's automate the mechanical checks so reviewers focus on logic, not style. Ruff in 2026 offers over nine hundred lint rules, running in roughly zero point two seconds on fifty thousand lines, versus about twenty seconds for Flake8. For types, keep mypy using the strict flag as your trusted CI reference, while Pyright gives faster editor feedback. Match each tool to its job: lint, types, security scanning, dependencies, and coverage. You can fold Bandit checks into Ruff's S ruleset for one fast pass. Run pre-commit for the inner loop, block merges in CI, and suppress findings only with written justification. Ask yourself: does your CI fail on a new bandit warning, or just log it? Next, we move to testing, coverage, and runtime signals.
awesomepython.devsafeguard.shdiffchecker.pro+22 min - 08Testing, Coverage, and Runtime SignalsNext, let's turn to testing, coverage, and runtime signals. With pytest, make parametrize your default for variations, keep fixtures narrow, and write deterministic tests with no shared mutable state. Ask of any suite: can these tests run in any order and still pass? Prefer branch coverage over line coverage by setting branch equals true. The percentage drops because the question got sharper, not because your code got worse. Set thresholds deliberately: roughly eighty percent overall as a CI floor, and one hundred percent on critical paths such as auth and payments. Coverage is a floor, not a goal, since a test that runs a line without asserting anything adds nothing. Add Hypothesis for property-based tests, which find about fifty times the mutations of an average unit test, and shrinking reduces each failure to a minimal example. Finally, check runtime signals: structured logging without personally identifiable information, latency and error metrics, timeouts on every external call, and profile before you optimize. Pick one of these checks and apply it to your own code today. That leads us into code review practices for Python teams.
augmentcode.comkodus.io2 min - 09Code Review Practices for Python TeamsNext, let's look at how Python teams run reviews in practice. Start from Google's standard. Approve once the change definitely improves code health, not when it reaches perfection. There is no perfect code, only better code. Reviewers check design, functionality, complexity, tests, naming, comments, style, and documentation. For example, ask whether a nested loop could be a dictionary lookup. Respond within one business day, and explain the why behind each comment. Prefix polish items with Nit: so the author knows what actually blocks the merge.
Authors carry half the process. Keep pull requests under four hundred lines of code, and state the why, the what, and how to test it. Self-review your diff before requesting review, and make sure the tests pass. Finally, if a linter can decide it, it is not a review comment. Add or fix the gate in CI instead. Try applying that test to your last review thread. Which comments could a tool have made?
augmentcode.comkodus.io2 min - 10A Practical Python Review LedgerLet's turn the checklist into a working ledger. Before you read code, copy the checklist next to the pull request. Give every rule one of three verdicts: PASS, FAIL, or N/A, and attach file and line evidence. N/A is still a decision, meaning no code of that kind appears in the diff or a green linter already covers it. A blank row means you never considered the rule. Write review comments only from the FAIL rows, one comment per finding. A green pipeline is not a clean change. Tests, Ruff, and mypy can all pass while this ledger returns six FAIL rows, so the checklist doesn't replace judgment; it makes sure judgment reaches every area. Sweep in severity order: correctness, Python pitfalls, concurrency, security, then performance. And hold these merge blockers: no cast(), no module-level mutable state, no except Exception in business code, and one name per concept. Try it on the next review you open. Next, we look at measuring quality without gaming the metrics.
augmentcode.comkodus.iosonarsource.com+22 min - 11Measuring Quality Without Gaming the MetricsNow let's talk about measuring quality without gaming the metrics. Group your signals into four families: static analysis, test results, review findings, and runtime behavior. SonarQube rates maintainability from A to E, derived from a technical debt ratio, where A means debt is five percent or less. CodeScene uses Code Health on a one to ten scale and detects twenty-five Python smells; keep files at nine or above to stay healthy. Track trends and baselines in frequently edited code, not just absolute scores. Relative churn predicts defects better than absolute churn, and code metrics beat design metrics for fault prediction. Yet no single metric wins. So apply Goodhart's law: never tie these numbers to individual performance. Ask of your own dashboard: would this change if developers gamed it? Next, we turn to technical debt, refactoring, and dependency management.
sonarsource.comaugmentcode.comkodus.io+21 min - 12Technical Debt, Refactoring, and Dependency ManagementNext, let us talk about technical debt and dependencies. Look for the signals: duplicated logic, tangled imports, missing tests, and code nobody wants to touch. Your review question is simple. Would you volunteer to change this module tomorrow?
Python version debt is concrete. As of October 2026, Python 3.10 has reached end of life, and 3.11 through 3.13 receive security fixes only. Quote the end-of-life date in any upgrade review.
Refactor safely. Write characterization tests that capture current behavior first, move in small incremental steps, and hide unfinished paths behind feature flags.
For dependencies, declare ranges in pyproject.toml, commit the lock file, and fail continuous integration when it is out of date. Use a lock file that pins every transitive dependency with hashes.
In 2026 you have options: uv with its universal lock file, Poetry two point x reading standard project metadata, pip-tools now under the Python Packaging Authority, and the standardized pylock format with only partial adoption.
Apply that drift check to one repository this week. That leads us to teaching and scaling quality practices.
sonarsource.comaugmentcode.comkodus.io+22 min - 13Teaching and Scaling Quality PracticesNow let's talk about teaching and scaling quality practices across a team. Onboarding is where this starts. Give newcomers starter checklists, pair them with experienced reviewers, and build reusable code tours. That matters: in a controlled study, learners using expert-guided tours scored eighty-three percent on comprehension quizzes, versus fifty-seven percent for AI-only tours. Second, align your training with your own repository. Using examples from the team's codebase reached eighty-nine percent completion, against fifty-one percent for generic content. Third, expect uneven gains. Short interventions helped less-prepared learners most, with a significant fifteen-point average improvement, while stronger learners sometimes regressed. So add differentiated pathways. Fourth, scale through shared Ruff and mypy configs, project templates, and written organization-wide standards, so consistency does not depend on individual reviewers. Finally, measure impact. Compare static analysis results and review metrics before and after, and watch for recurring finding categories. A category that keeps appearing signals an undocumented standard. Next, we bring this together in the capstone: auditing a real Python codebase.
sonarsource.comaugmentcode.comkodus.io+22 min - 14Capstone: Auditing a Real Python CodebaseLet's close by putting the criteria to work. Your audit follows four stages. Inventory the codebase, run the automated scans, do the manual review, then rank the risks.
The automated pass runs on the resolved lockfile: Ruff for lint, mypy for types, Bandit for security patterns, pip-audit for vulnerable dependencies, and pytest-cov for coverage. Treat a score without a justification as a bug. Every number needs evidence, and the number is only a summary of the findings.
Each report entry follows the same anatomy: the finding, its severity, the failure mode, the file and line, the fix, and the rule or CWE it maps to.
Run the review ledger on a sample repo. Record pass, fail, or not applicable for each rule with file and line evidence. Then defend your priorities. Why does this finding block the merge and that one wait?
For next steps, write a roadmap with a baseline, a target, and one owner per workstream.
Your artifact is a defensible audit, not a dashboard. Thank you for joining this course. Go audit something real, and let the evidence set your priorities.
augmentcode.comkodus.iosonarsource.com+22 min
Take the deck with you
Download this course as a file — free, no sign-up needed.
- PDF handoutEvery slide page, ready to print or share.15 pages · 3.5 MBDownload
- Narrated PowerPointThe deck that presents itself — every slide carries the digital human's narration video.15 pages · 15.2 MBDownload
- PowerPoint slidesThe full deck as a .pptx — open it in PowerPoint, Keynote, or Google Slides.15 pages · 3.4 MBDownload
Free to use in your own training — please keep the PersonWise credit page at the end.
Have your own deck? Turn it into a course
Sources consulted
Web sources consulted while building this course.
- What is Code Quality? Definition Guide & How-to Improve and Measure | Sonar — sonarsource.com
- Python Code Review Checklist: 25 Things to Check in 2026 | Augment Code — augmentcode.com
- Python Code Quality | Checklist — kodus.io
- What Is Code Quality in Software? | Official Qodo Glossary — qodo.ai
- Python Code Quality: Best Practices and Tools – Real Python — realpython.com
- ISO/IEC 25010:2023 - Systems and software engineering — Systems and software Quality Requirements and Evaluation (SQuaRE) — Product quality model — iso.org
- Standard - Systems and software engineering — Systems and software Quality Requirements and Evaluation (SQuaRE) — Product quality model (ISO/IEC 25010:2023, IDT) SS-ISO/IEC 25010:2026 - Swedish Institute for Standards, SIS — sis.se
- BS ISO/IEC 25010:2023 - TC | 30 Nov 2023 | BSI Knowledge — knowledge.bsigroup.com
- UNI CEI ISO/IEC 25010:2024 - UNI Ente Italiano di Normazione — unistore.uni.com
- Software quality | IEEE Technology Navigator — technav.ieee.org
- Google Style Guides | Style guides for Google-originated open-source projects — google.github.io
- The Little Book of Python Anti-Patterns - QuantifiedCode — docs.quantifiedcode.com
- internal/config/rules/rule_docs/python.md — github.com
- Python Bugs // Teardown — hed0rah.github.io
- Anti Patterns – Toby's Documentation — tobyqin.cn
- Python Linters and Type Checkers: Ruff, mypy, Pyright and more | Awesome Python — awesomepython.dev
- Python Code Review Tools Compared (2026) — safeguard.sh
- Python Static Code Analysis: 2026 Tools & Workflow Guide — diffchecker.pro
- How to Check Python Code for Security Issues — safeguard.sh
- Rafter - Python Security Tools: What Developers Should Use in 2026 — rafter.so