新卒1年目で、pylintに3本・nilearnに1本、計4本のPRを送り、全てマージされた。この記事ではpylintでのバむ修正3本の話をまとめる。「OSSにコントリビュートしてみたいけど何から始めれば」という人の参考になれば。
pylintとは
Pythonの静的コード解析ツール。コードのスタイル違反・バグになりうるパターン・不要なコードを検出する。PEP8準拠チェックのリンターよりも一歩踏み込んだ解析ができる。
直したバグ3本
PR #11081 — superfluous-parens(C0325)の見逃し
問題
in の後ろに来る単一リテラルを囲む不要な括弧が検知されていなかった。
# これが警告されるべきなのに、スルーされていた
if x in ("foo"):
pass
修正内容
pylint/checkers/format.py の _check_keyword_parentheses メソッドを条件化。タプル・二重カッコのジェネレータ式・通常の式の場合は除外して、既存の回帰ゑ防いだ。
# タプルや二重カッコは除外してOK
if x in ("foo", "bar"): # タプル → 警告なし
pass
if x in ("foo"): # 単一リテラル → C0325 を出す
pass
functionalテスト4件とnews fragmentを追加して送った。
PR #11082 — implicit-str-concat(W1404)の誤検知
問題
raw文字列と非raw文字列の暗黙連結に対して誤った警告が出ていた。
# r"\d" と "\n" はマージ不可能(raw/非rawの混在)
# 意図的な書き方なのに W1404 が出ていた
pattern = r"\d" "\n"
raw文字列と通常文字列をマージすると意味が変わる。つまり「暗黙連結は意図的」なのに、pylintが「これは不要な連結だ」と誤検知していた。
修正内容
strings.py に _is_raw_string_token ヘルパーを追加し、string_tokens に生のトークン情報を保持するようにした。これでraw/非rawの混在ケースを正確に識別できるようにした。
def _is_raw_string_token(token: str) -> bool:
return token.upper().startswith("R")
PR #11083 — unnecessary-comprehension(R1721)の誤提案
問題
辞書内包表記に対して間違ったリファクタリング提案が出ていた。
# pylint が dict(d) を提案していたが、これは間違い
result = {a: b for a, b in d}
# 正しくは dict(d.items())
d はキーとバリューのペアを返す何らかのイテラブルのはずで、そのまま dict(d) を呼んでも意図通りにならない。
修正内容
refactoring_checker.py にケースを追加して、提案生成ロジックを _unnecessary_comprehension_suggestion というヘルパーに抽出した。これにより提案の分岐が整理され、正確な提案が出るようになった。
実際の進め方
1. Issueを見つける
Good First Issueから入った。pylintはissue数が多く、未トリアージのものも含めると比較的入りやすい。
2. 手元で再現する
まずバグを手元で確実に再現させる。これが一番大事で、再現できないまま修正すると見当違いになる。
3. AIと一緒に議論する
バグの原因調査と修正方針の議論はClaudeと一緒に行った。「このコードの流れ的にどこが怪しいか」「このケースを外すとなぜ既存テストが壊れるか」といった議論を繰り返すと、コードベースの理解が早まる。
ただし最終的なコード検証と動作確認は必ず自分でやる。OSSはメンテナーにレビューされるので、AIに任せっぱなしで出すと粗が出る。
4. テストを書��
functionalテストとunit testの両方がある。tests/functional/ にある .py ファイルが期待する警告を .txt で定義するスタイルは独特なので、既存のテストをいくつか読んでからにするとよい。
5. PRを送る
タイトルにfix:/feat:などの接頭辞は不要。バッククォートでissue番号や関連識別子を囲むのは歓迎される。
ハマった罠
-
news fragmentのファイル名に拡張子はつけない —
doc/whatsnew/fragments/<issue>.<type>のtypeはfalse_negativeなど、towncrier形式に従う - blackはtests/functionalを除外している — fixtureファイルなのでフォーマット対象外。知らないと「ぜblackが通っているのに形式が違う?」と混乱する
- ruffのline-length = 79が厳しい — コメント行も対象。長い文章をコメントに書くとE501で落ちる
- GitHub ActionsのフルテストはメンテナーOKまで走らない — 初コントリビュータはCIが全部流れないので、手元でpytestを通してから待つしかない
- PRタイトルの形式 — fix:/feat: などのConventional Commits形式は不要(むしろ付けないほうが馴染む)
まとめ
新卒の今やるべき理由が2つある。
1つ目は、就職活動の実績として機能する。「OSSに貢献した」は口だけではなく、PRのURLで示せる。書類・面接どちらにも使える。
2つ目は、**「世界中にレビューされるコード」を書か何が誗める。社内コードと違い、知らない人間に批判的に読まれる前提で曼かと送しからにするとよい。
コードの品質がそのまま世界に公開さらo���
��G�
/���,�8ikX�.8�iz�8Nj�^���8~8(N8>8n8�8�8�)��8+�8�ZH�8(�8(�8 ��Z�����8�XZ�8n89�8;�8+�8^8(�8�K��88>8(�8�[�^8�8�88~8�8�8N8 ����Р�22X�.�>8:�8;>8������Ɩ�B4��E$�%UD��r8�8N88�҆�GG3����Ɩ�B�&VGF�VF�72���V���FW7B�FWfV���V�E�wV�FR�6��G&�'WFR�F����v��Bf�'7B�77VR( B�F���҆�GG3���v��Ff�'7F�77VR�FWb���wVvR��F��␢��ikX�.8�8;>8+�8;>8*.8��5>8+>8;>88�8:�89>8:^8;�8+~89�89>8;>8��$~j��h���ix�e��g�*lWJ��ZZ]K���K�ZKX�[�L
LK�][\��YXL�M�͍XLY�L�،JB