はじめに

Pythonでは標準出力へのprint()と、標準ライブラリloggingによるログ出力が併存している。
しかし実務コードでは、これらが無秩序に混在したまま運用環境に入り込むケースが後を絶たない。

レビューアーの役割は、この混在を単なるコーディングスタイルの違いとして片付けるのではなく、

  • 責務の混同
  • 運用時のトレース困難性
  • テスト環境での情報管理の不一致

といった構造的リスクとして捉え、設計そのものの是正に踏み込むことである。

典型例:printとloggingが混在したコード

問題のある出力混在コード
def fetch_data(url):
    print("Fetching data...")  # デバッグ
    response = requests.get(url)
    if response.status_code != 200:
        logging.error(f"Failed to fetch: {url}")
    return response.json()
Comment
@Reviewer: `print()`はログの制御が不可能で、本番では標準出力に混在します。ロギングレベル付きの構造的出力に統一すべきです。

このように、デバッグ出力とエラー記録の責務が別形式で書かれることで、処理の意図が不明瞭かつ運用制御が困難になる。

構造的改善:ログ出力に責務と粒度を与える

ログ構造を明示した改善案
import logging

logger = logging.getLogger(__name__)

def fetch_data(url):
    logger.debug("Fetching data...")
    response = requests.get(url)
    if response.status_code != 200:
        logger.error(f"Failed to fetch: {url}")
    return response.json()

改善点:

  • printをlogger.debugに置換し、ログ制御下に統合
  • 責務を「人向けの出力」から「観測可能なログ」に昇華
  • ログ出力のON/OFF、出力先、書式の外部制御が可能になる

構造の違い

UML Diagram
UML Diagram

ログ出力に統一されることで、出力の粒度と制御構造が明確化され、環境ごとに挙動を切り替え可能になる。

print使用の是正指摘

ログ統一に関するレビューやりとり
def process():
    print("処理を開始します")
    result = do_something()
    if not result:
        logging.warning("処理失敗")
Comment
@Reviewer: `print`が標準出力に混入し、ログとは分離されてしまいます。ログファシリティに統一することで、情報の整合性と制御性を確保できます。

ログ設計でレビューすべき観点

構造上の兆候 レビュー観点 指摘内容と提案
printとloggingの混在 情報粒度の不統一 ログレベル設計と出力先設計を導入
printのみに依存 運用ログが標準出力に流れている loggerによる制御・保存を検討
logger未初期化 全体でlogging.basicConfig未使用 アプリ共通初期化を設計に加える
ログレベルが全てerror 情報の粒度が粗すぎてトレース不能 debug/info/warningの使い分け導入
ハードコードされたprint出力 出力制御ができずテストにも干渉 ロガー注入やMock対応設計を検討

運用と開発の責務を分ける:ログレベルと出力戦略

  • debug: 開発時の詳細追跡(本番ではOFF)
  • info: ユーザー操作や主要なフロー記録
  • warning: 異常兆候、だが処理継続可能
  • error: 処理失敗、復旧処理も必要
  • critical: 重大障害、即時介入対象

レビューアーは、ログレベルの意味付けと使い分けの方針が設計に含まれているかを確認すべきである。

ログ構造の統一設計(導入のスケルトン)

ロギング初期化の共通構造
import logging

def init_logging(level=logging.INFO):
    logging.basicConfig(
        format="%(asctime)s %(levelname)s [%(name)s]: %(message)s",
        level=level
    )
使用側
logger = logging.getLogger(__name__)
logger.info("アプリケーション起動")

このような構造を設計段階で提供しておけば、すべてのモジュールが統一された形式でログを出力できるようになる。

まとめ:レビューアーがログ設計をどう見るか

printとloggingの混在は、単なる書き方の差ではなく、可観測性・運用性・構造性に直結する設計問題である。

レビューアーは以下の観点で構造を評価すべきである:

  • 出力がどこに向かい、どう制御されているか?
  • 出力が一貫した形式(レベル、フォーマット)を持っているか?
  • 出力手段が本番・テスト・ローカルで切り替え可能か?
  • 標準出力のprintに依存したまま放置されていないか?

ログは開発者の“つぶやき”ではなく、システムの状態と責任を伝える構造化された情報である。
その設計にレビューの光を当てることが、コード全体の品質と運用力を高める鍵となる。