1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

TypedDictをラッパー関数作成に活用する

Last updated at Posted at 2025-06-23

はじめに

以前、TypedDictを利用した「Options Objectパターン」の手法について
ふれていたが、使いどころが模索できていないままでした。
今回はコードを書く中で見つけた使いどころについて紹介します。

ラッパー関数作成時での使いどころ

下記は「pywinauto」を利用し、指定要素の子に位置する
ボタン要素を取得する処理です。

parent_window_specification_object.child_window(
    class_name="Button", title="保存"
)

この処理をラップする際には、
引数で親要素オブジェクトと検索条件の2種類を渡す必要がありますが
必ず渡す親要素オブジェクトと、子要素の検索条件を分離した方が読みやすくなります。

その点を考慮し、TypedDictを利用して
引数を役割をごとに分離した以下のようなラッパー関数を作成してみました。

from typing import Any, NotRequired, TypedDict

from pywinauto import WindowSpecification

# child_window()に渡す引数の管理
ChildSearchCriterias = TypedDict(
    "ChildSearchCriterias",
    {"class_name": NotRequired[str], "title": NotRequired[str], "found_index": NotRequired[int]},
)


def child_window_wrapper(
    parent_element: WindowSpecification, child_search_criterias: ChildSearchCriterias
) -> WindowSpecification:
    """child_windowメソッドのラッパー関数
    Args:
        parent_element (WindowSpecification): 親要素のオブジェクト
        child_search_criterias (ChildSearchCriterias): 子要素の検索条件
        
    Returns:
        WindowSpecification: 探索結果のオブジェクト
    """

    criterias: dict[str, Any] = {}
    if child_search_criterias.get("class_name"):
        criterias["class_name"] = child_search_criterias["class_name"]
    if child_search_criterias.get("title"):
        criterias["title"] = child_search_criterias["title"]
    # 0以上の数値型のみを引数とする
    index_value: int | None = child_search_criterias.get("found_index")
    if isinstance(index_value, int) and index_value >= 0:
        criterias["found_index"] = index_value

    return parent_element.child_window(**criterias)

このように設計する利点としては、ラッパー関数を呼び出す際の渡す引数が
(必須要素, {オプション要素})の形式となり、可読性が向上しています。

ラッパー関数を呼び出す際は、以下のようになり役割ごとで分離でき、
メソッド引数についても、引数名指定と同じように利用ができるのも利点です。

# ラップせずに利用(比較用)
parent_window_specification_object.child_window(
    class_name="Button", title="保存"
)

# 自作ラッパー関数を利用
child_window_wrapper(
    parent_window_specification_object,
    {"class_name": "Button", "title": "保存"},
)

補足として、ラッパー関数の引数にDict型で渡すので、
そのままキーワード可変長引数(**kwargs)で、ラッピング対象へ渡すことも可能です。
しかし、その場合だと誤った引数名を指定して渡してしまう可能性が考えられます。
その部分についても、TypedDictを使うことで予防しています。

あとがき

Pythonにおける型定義関連の部分はバージョンが上がるごとに充実してきており
個人的には注目している箇所の1つであり、どんどん使いたい派です。

今回はpywinautoを一例として出したが、
他にもselenium、playwrightのラッパー関数を作成する場合や
Requestsのように引数が多数あるメソッドをラップする際にも
活用できると考えています。

参考

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?