AgentStack
SKILL verified MIT Self-run

Python Code Style

skill-owenlamont-agent-skills-python-code-style · by owenlamont

Write Python source to this project's standards. Use when authoring or refactoring Python code and deciding on style, type hints, docstrings, comments, imports, or language idioms.

No reviews yet
0 installs
4 views
0.0% view→install

Install

$ agentstack add skill-owenlamont-agent-skills-python-code-style

✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access Used
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

Are you the author of Python Code Style? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

Python Code Style

Standards for writing Python source in this project.

Style guide and docstrings

  • Follow the

Google Python Style Guide for all code, including its Google-style docstrings.

Type hints

  • Type everything with the strongest type that still matches how the value is used —

specific to its semantics/interface, which for an iterated-only parameter is Iterable[X] rather than list[X].

  • Use modern type-hint syntax: lowercase built-in generics (list, dict, tuple),

X | None over Optional[X], and collections.abc types (Iterable, Sequence, Mapping).

  • Model categorical values as a StrEnum (or another Enum), not a bare str, so the

permitted values are explicit and type-checked.

  • When a dict's keys and value types are known ahead of time, use a TypedDict or a

dataclass rather than a plain dict, or a Pydantic model when you also need runtime validation.

  • Type-hint module-level constants with Final, name them ALL_CAPS

(MAX_RETRIES: Final = 3), and prefix module-local (non-exported) ones with an underscore (_MAX_RETRIES); function- and class-local values need neither Final nor ALL_CAPS. Give magic numbers a named constant rather than inlining them.

  • Don't use typing.cast(); fix the underlying type error instead of suppressing it.
  • Keep Any to a minimum by giving values a specific type wherever one fits. For a

genuinely untypable value, prefer Any over object (which forces isinstance/casts before use and conveys no intent).

  • type: ignore should almost never be used — only for third-party packages with no

typing or with dynamic typing.

  • Prefer explicit typed signatures and attribute access over runtime introspection

(getattr/hasattr/__dict__) and *args/**kwargs passthrough; both defeat static type checking, autocomplete, and grep-based refactoring.

  • Dispatch on a finite set of values with an explicit mapping or match/case rather

than an if/elif chain.

Functions and data modelling

  • Make invalid states unrepresentable: model data so bad combinations can't be

constructed — an Enum instead of several booleans, a sub-model instead of loosely related flat fields, one canonical representation of "empty" — and minimise optional/None-able fields. Prefer it to runtime validation that patches bad input.

  • Don't mutate objects passed in as arguments; copy and return a new value (recreate

Pydantic models). In-place mutation is a surprising side effect that hampers reasoning and testing.

  • Make every parameter keyword-only with a leading bare * when any of these holds:

three or more parameters, two or more of the same type, or any boolean parameter (prevents argument-order and boolean-trap bugs).

  • Group related values that travel together into a named dataclass/model rather than a

positional tuple, and defer extracting a shared helper until the duplication is real.

Comments and docstrings

  • Keep comments to an absolute minimum. Achieve readability through meaningful class,

function, and variable names instead — and prefer extracting a well-named intermediate variable over a comment that explains a complex expression.

  • Suffix variables and function arguments with their unit of measure where one applies

(e.g. timeout_ms, payload_size_bytes, duration_seconds), so the name carries the unit.

  • Name for meaning rather than implementation, write boolean predicates positively to

avoid double negation, don't use generic module names like utils.py, and keep acronyms fully upper-case (HTTPClient, not HttpClient).

  • Don't write module- or class-level docstrings. Keep function docstrings only, and

short; put a CLI's usage narrative in its command/argument help (e.g. Typer), not a module docstring.

  • Public functions should have docstrings. Parameters only need to be documented when

the name and type hint don't convey their full semantics.

  • Always document non-obvious side effects, the exceptions a function raises, and

whether numeric range bounds are inclusive or exclusive, even when the parameters themselves are self-evident.

  • Private functions (single-underscore prefix, per PEP 8) used within a module don't need

docstrings, unless their names and type hints aren't sufficient to convey their semantics.

  • Comments should only be used to explain:
  • unavoidable code smells arising from third-party package use,
  • the reason for temporary dependency version pinning (e.g. linking an unresolved

GitHub issue), or

  • opaque code, non-obvious trade-offs, or workarounds.
  • Link every suppression (noqa, type: ignore, a coverage pragma) to a tracking

issue or a one-line justification.

Imports

  • Keep all imports at the top of the module unless an import must be local to avoid a

circular import.

  • Use absolute imports only — no relative imports.
  • Don't import private (underscore-prefixed) names across modules; if another module

needs it, make it public and place it in the module its domain belongs to.

  • Keep __init__.py files empty: no re-exports; import each symbol from the module that

defines it. (Exception: deliberately curated public-API packages populate __init__.py to simplify import paths.)

  • Don't add from __future__ import annotations; the project's Python version defers

annotation evaluation already.

Language idioms

  • Use the most modern Python idioms and syntax allowed by the project's minimum

supported Python version.

  • Prefer immutable containers (tuple, frozenset) for fixed or read-only data,

including module-level constants; use mutable containers only when the data changes, and default_factory for any mutable dataclass/Pydantic default.

  • Use pathlib.Path (not os/os.path) for filesystem work and as path-argument

types, and reach for stdlib helpers (Counter, itertools, str.removeprefix, //) over hand-rolled equivalents.

  • Build collections with comprehensions or generator expressions rather than

loop-and-append. Pass a generator (not a materialised list) to one-shot consumers like str.join, sum, or pd.concat.

  • Use contextlib.suppress(...) instead of an empty try/except: pass; use float

literals in float arithmetic and never compare floats with == (use math.isclose or an explicit tolerance).

  • Use a plain string literal, not an f-string, when there's nothing to interpolate.
  • Keep non-trivial SQL in .sql files loaded at runtime, not embedded in Python string

literals, so SQL tooling can lint and format it.

  • Compare versions with packaging.version.Version, not string or tuple comparison

(which sorts e.g. 0.10 before 0.9).

Testing

Test authoring and layout conventions live in the python-pytest skill.

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet — be the first.

Versions

  • v0.1.0 Imported from the upstream source.