skills/code-analysis/code-comment-generator/SKILL.md
Generates code comments that explain non-obvious intent, constraints, and tradeoffs — not what the code already says. Use when code is correct but opaque, when documenting for future maintainers, or when a function's why is harder to see than its what.
npx skillsauth add santosomar/general-secure-coding-agent-skills code-comment-generatorInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Good comments explain why, not what. The code already says what. If you're narrating the code, delete the comment and make the code clearer instead.
| Worth commenting | Why | | ------------------------------------------------- | ----------------------------------------------------- | | A non-obvious constraint the code depends on | "x is sorted here because caller guarantees it" | | A tradeoff that was made deliberately | "O(n²) is fine — n ≤ 20 by construction" | | Why the obvious approach is wrong | "Can't use .sort() — caller holds references into this list" | | A workaround for an external bug | "libfoo 2.3 returns NULL here; remove when we upgrade" | | Magic numbers with a source | "15s — AWS Lambda cold start p99 + margin" | | Coupling to something far away | "Must match the regex in nginx.conf" | | A subtle correctness argument | "Safe to read without lock: only written at startup" |
| Skip | Why |
| ------------------------------------------------- | ----------------------------------------------------- |
| i++ // increment i | The code says that. Noise. |
| // loop over items above for item in items: | Same. |
| Restating the function name in a docstring | def save_user(): """Saves user.""" — waste. |
| Commented-out code | That's what git is for. Delete it. |
| // TODO: fix this later | Unactionable. TODO: what and why not now? |
| Comments that will rot | "Called from foo.py:42" — until foo.py changes. |
If you rename all the variables and the comment still makes sense, it's a good comment (explains intent). If the comment is now wrong, it was restating the code.
# BEFORE rename
x = compute_total(items)
# Store the total ← restating. Bad.
# AFTER rename test
q = compute_total(items)
# Store the total ← now the comment is confusing. It was bad.
vs.
# Compute total before filtering — downstream needs the pre-filter sum for the audit log.
x = compute_total(items)
items = [i for i in items if i.active]
Rename x → comment still explains why the ordering matters. Good.
Uncommented code:
def reconnect(self):
delay = 0.1
for attempt in range(8):
try:
self._connect()
return
except ConnectionError:
time.sleep(delay + random.uniform(0, delay))
delay = min(delay * 2, 5.0)
raise ConnectionError("exhausted retries")
What the code already says: retries 8 times, exponential backoff, cap at 5s, jitter. Don't comment any of that.
What's not obvious:
def reconnect(self):
# Full jitter would be random.uniform(0, delay), but that occasionally
# produces near-zero sleeps that hammer the server. Half-jitter (delay + uniform(0, delay))
# guarantees at least `delay` between attempts — gentler on the remote.
delay = 0.1
for attempt in range(8): # 8 attempts × max 10s each ≈ 80s worst case — under the 90s LB timeout
try:
self._connect()
return
except ConnectionError:
time.sleep(delay + random.uniform(0, delay))
delay = min(delay * 2, 5.0)
raise ConnectionError("exhausted retries")
Two comments. The first explains a non-obvious design choice (why half-jitter, not full-jitter). The second explains a magic number in terms of an external constraint (LB timeout).
Docstrings are a different animal: they're for callers, not maintainers. They should state:
They should NOT describe the implementation. If the implementation changes but the contract doesn't, the docstring shouldn't need updating.
// increment counter above counter++. Ever.# list comprehension above a list comprehension — the reader knows Python or they don't; the comment won't help either way.TODO without a what and a why-not-now. TODO(#1234): remove this shim once libfoo 3.0 ships (expected Q2) is actionable. TODO: fix is not.x = get_total() # x is the total → just total = get_total().For each comment proposed:
## <file:line>
### Current code
<snippet>
### Proposed comment
<the comment>
### Why this comment
<what non-obvious thing it explains — constraint, tradeoff, coupling, workaround>
### Not commenting
<things in this snippet that looked comment-worthy but aren't — the code says it>
development
Extracts human-readable pseudocode from a verified formal artifact (Dafny, Lean, TLA+) while preserving the verified properties as annotations, so the proof-carrying logic can be reimplemented in a production language. Use when porting verified code to an unverified target, when documenting what a formal spec actually does, or when handing a verified algorithm to an implementer.
development
Translates natural-language or pseudocode descriptions of concurrent and distributed systems into TLA+ specifications ready for the TLC model checker. Identifies state variables, actions, type invariants, safety properties, and liveness properties from the description. Use when formalizing a protocol, when the user describes a distributed algorithm to verify, when designing a consensus or locking scheme, or when starting formal verification of a concurrent system.
testing
Reduces a TLA+ model so TLC can actually check it — shrinks constants, adds state constraints, abstracts data, or applies symmetry — when the state space is too large to enumerate. Use when TLC runs out of memory, when checking takes hours, or when a spec works at N=2 and you need confidence at larger scale.
development
TLA+-specific instance of model-guided repair — reads a TLC error trace, identifies the enabling condition that should have been false, strengthens the corresponding action, and maps the fix to source code. Use when TLC reports an invariant violation or deadlock and you have the code-to-TLA+ mapping from extraction.