コンテンツにスキップ

pytilpack.web

pytilpack.web

Web関係の一般的な処理をまとめたモジュール。

get_safe_url(target, host_url, default_url)

ログイン時のリダイレクトとして安全なURLを返す。

引数:

名前 タイプ デスクリプション デフォルト
target str | None

リダイレクト先のURL

必須
host_url str

ホストのURL

必須
default_url str

デフォルトのURL

必須

戻り値:

タイプ デスクリプション
str

安全なURL

ソースコード位置: pytilpack/web.py
def get_safe_url(target: str | None, host_url: str, default_url: str) -> str:
    """ログイン時のリダイレクトとして安全なURLを返す。

    Args:
        target: リダイレクト先のURL
        host_url: ホストのURL
        default_url: デフォルトのURL

    Returns:
        安全なURL
    """
    if target is None or target == "":
        return default_url
    ref_url = urllib.parse.urlparse(host_url)
    test_url = urllib.parse.urlparse(urllib.parse.urljoin(host_url, target))
    if test_url.scheme not in ("http", "https") or ref_url.netloc != test_url.netloc:
        logger.warning(f"Invalid next url: {target}")
        return default_url
    return target

check_status_code(status_code, valid_status_code)

ステータスコードのチェック。

ソースコード位置: pytilpack/web.py
def check_status_code(status_code: int, valid_status_code: int) -> None:
    """ステータスコードのチェック。"""
    if status_code != valid_status_code:
        raise AssertionError(f"ステータスコードエラー: {status_code} != {valid_status_code}")

check_content_type(content_type, valid_content_types)

Content-Typeのチェック。

ソースコード位置: pytilpack/web.py
def check_content_type(content_type: str, valid_content_types: str | typing.Iterable[str] | None) -> None:
    """Content-Typeのチェック。"""
    if valid_content_types is None:
        return None
    if isinstance(valid_content_types, str):
        valid_content_types = [valid_content_types]
    # ; charset=utf-8などが付いている場合があるため、簡易的にstartswithでチェックする
    if not any(content_type.startswith(c) for c in valid_content_types):
        raise AssertionError(f"Content-Typeエラー: {content_type} != {valid_content_types}")
    return None

check_html(input_stream, strict=False)

HTMLのチェック。

ソースコード位置: pytilpack/web.py
def check_html(input_stream: typing.Any, strict: bool = False) -> None:
    """HTMLのチェック。"""
    parser = html5lib.HTMLParser(debug=True)
    _ = parser.parse(input_stream)
    if len(parser.errors) > 0:
        errors = [
            f"{position}: {html5lib.constants.E[errorcode] % datavars}" for position, errorcode, datavars in parser.errors
        ]
        if strict:
            error_str = "\n".join(errors)
            raise AssertionError(f"HTMLエラー: {error_str}")
        for error in errors:
            logger.warning(f"HTMLエラー: {error}")