From b3216d078b8589e889bb27385c29200029a66c91 Mon Sep 17 00:00:00 2001 From: Mark Nottingham Date: Thu, 14 Dec 2023 12:38:14 +1100 Subject: [PATCH] Stop using **kw: Any in formatters --- redbot/cli.py | 5 ++++- redbot/formatter/__init__.py | 19 ++++++++++++++++--- redbot/formatter/har.py | 8 ++++---- redbot/formatter/html.py | 6 ++++-- redbot/formatter/html_base.py | 9 +++++---- redbot/formatter/slack.py | 7 ++++--- redbot/formatter/text.py | 24 +++++++++++------------- redbot/webui/__init__.py | 22 ++++++++++++++-------- redbot/webui/saved_tests.py | 10 ++++++---- redbot/webui/slack.py | 9 ++++++--- 10 files changed, 74 insertions(+), 45 deletions(-) diff --git a/redbot/cli.py b/redbot/cli.py index a237a309..e44162b5 100755 --- a/redbot/cli.py +++ b/redbot/cli.py @@ -49,7 +49,10 @@ def main() -> None: resource.set_request(args.url) formatter = find_formatter(args.output_format, "text", args.descend)( - config, resource, output, tty_out=sys.stdout.isatty(), descend=args.descend + config, + resource, + output, + {"tty_out": sys.stdout.isatty(), "descend": args.descend}, ) formatter.bind_resource(resource) diff --git a/redbot/formatter/__init__.py b/redbot/formatter/__init__.py index f4c286b5..4f3cb512 100644 --- a/redbot/formatter/__init__.py +++ b/redbot/formatter/__init__.py @@ -9,12 +9,13 @@ import locale import sys import time -from typing import Optional, Any, Callable, List, Dict, Type, TYPE_CHECKING +from typing import Optional, Any, Callable, List, Dict, Tuple, Type, TYPE_CHECKING import unittest from markdown import Markdown import thor from thor.events import EventEmitter +from typing_extensions import TypedDict if TYPE_CHECKING: from redbot.resource import HttpResource # pylint: disable=cyclic-import @@ -68,6 +69,18 @@ def available_formatters() -> List[str]: return _formatters +class FormatterParams(TypedDict): + config: SectionProxy + resource: "HttpResource" + output: Callable[[str], None] + params: Dict[str, Any] + + +FormatterArgs = Tuple[ + SectionProxy, "HttpResource", Callable[[str], None], Dict[str, Any] +] + + class Formatter(EventEmitter): """ A formatter for HttpResources. @@ -84,7 +97,7 @@ def __init__( config: SectionProxy, resource: "HttpResource", output: Callable[[str], None], - **kw: Any, + params: Dict[str, Any], ) -> None: """ Formatter for the given URI, writing @@ -96,7 +109,7 @@ def __init__( self.resource = resource self.lang = config["lang"] self.output = output # output file object - self.kw = kw # extra keyword arguments + self.kw = params self._markdown = Markdown(output_format="html") def bind_resource(self, display_resource: "HttpResource") -> None: diff --git a/redbot/formatter/har.py b/redbot/formatter/har.py index 499c42eb..9296086d 100644 --- a/redbot/formatter/har.py +++ b/redbot/formatter/har.py @@ -6,10 +6,10 @@ import datetime import json from typing import Optional, Any, Dict, List -from typing_extensions import TypedDict +from typing_extensions import TypedDict, Unpack from redbot import __version__ -from redbot.formatter import Formatter +from redbot.formatter import Formatter, FormatterArgs from redbot.resource import HttpResource from redbot.type import StrHeaderListType @@ -35,8 +35,8 @@ class HarFormatter(Formatter): name = "har" media_type = "application/json" - def __init__(self, *args: Any, **kw: Any) -> None: - Formatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + Formatter.__init__(self, *args) self.har: HarDict = { "log": { "version": "1.1", diff --git a/redbot/formatter/html.py b/redbot/formatter/html.py index 3e245ad6..22059dba 100644 --- a/redbot/formatter/html.py +++ b/redbot/formatter/html.py @@ -8,11 +8,13 @@ from typing import Any, List, Match, Tuple from urllib.parse import urljoin +from typing_extensions import Unpack from httplint import get_field_description from httplint.note import Note, levels, categories import thor.http.error as httperr from redbot import __version__ +from redbot.formatter import FormatterArgs from redbot.formatter.html_base import ( BaseHtmlFormatter, e_query_arg, @@ -77,8 +79,8 @@ class SingleEntryHtmlFormatter(BaseHtmlFormatter): name = "html" - def __init__(self, *args: Any, **kw: Any) -> None: - BaseHtmlFormatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + BaseHtmlFormatter.__init__(self, *args) self.templates.filters.update( { "header_present": self.format_header, diff --git a/redbot/formatter/html_base.py b/redbot/formatter/html_base.py index 2fadd6e0..831f4a85 100644 --- a/redbot/formatter/html_base.py +++ b/redbot/formatter/html_base.py @@ -3,15 +3,16 @@ import json import os import time -from typing import Optional, Any, List, Tuple +from typing import Optional, List, Tuple from urllib.parse import urljoin, urlencode, quote as urlquote import httplint from jinja2 import Environment, PackageLoader, select_autoescape from markupsafe import Markup, escape +from typing_extensions import Unpack import redbot -from redbot.formatter import Formatter, relative_time, f_num +from redbot.formatter import Formatter, FormatterArgs, relative_time, f_num from redbot.webui.captcha import CAPTCHA_PROVIDERS NL = "\n" @@ -65,8 +66,8 @@ class BaseHtmlFormatter(Formatter): ), ) - def __init__(self, *args: Any, **kw: Any) -> None: - Formatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + Formatter.__init__(self, *args) self.templates.filters.update( { "f_num": f_num, diff --git a/redbot/formatter/slack.py b/redbot/formatter/slack.py index 3dbf95fb..0483bf01 100644 --- a/redbot/formatter/slack.py +++ b/redbot/formatter/slack.py @@ -4,11 +4,12 @@ import json from typing import Optional, Any, List, Dict, Union +from typing_extensions import Unpack from httplint import HttpResponseLinter from httplint.note import categories, levels -from redbot.formatter import Formatter +from redbot.formatter import Formatter, FormatterArgs from redbot.resource import HttpResource from redbot.resource.fetch import RedHttpClient @@ -37,8 +38,8 @@ class SlackFormatter(Formatter): levels.INFO: ":information_source:", } - def __init__(self, *args: Any, **kw: Any) -> None: - Formatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + Formatter.__init__(self, *args) def start_output(self) -> None: pass diff --git a/redbot/formatter/text.py b/redbot/formatter/text.py index 83b2740d..b5843532 100644 --- a/redbot/formatter/text.py +++ b/redbot/formatter/text.py @@ -6,13 +6,14 @@ import operator import re import textwrap -from typing import Any, List, Optional +from typing import List, Optional +from typing_extensions import Unpack from httplint import HttpResponseLinter from httplint.note import Note, levels, categories import thor.http.error as httperr -from redbot.formatter import Formatter +from redbot.formatter import Formatter, FormatterArgs from redbot.resource import HttpResource NL = "\n" @@ -44,8 +45,8 @@ class BaseTextFormatter(Formatter): error_template = "Error: %s\n" - def __init__(self, *args: Any, **kw: Any) -> None: - Formatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + Formatter.__init__(self, *args) self.verbose = False def start_output(self) -> None: @@ -146,9 +147,6 @@ class TextFormatter(BaseTextFormatter): name = "txt" media_type = "text/plain" - def __init__(self, *args: Any, **kw: Any) -> None: - BaseTextFormatter.__init__(self, *args, **kw) - def finish_output(self) -> None: BaseTextFormatter.finish_output(self) @@ -156,8 +154,8 @@ def finish_output(self) -> None: class VerboseTextFormatter(TextFormatter): name = "txt_verbose" - def __init__(self, *args: Any, **kw: Any) -> None: - TextFormatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + TextFormatter.__init__(self, *args) self.verbose = True @@ -170,8 +168,8 @@ class TextListFormatter(BaseTextFormatter): media_type = "text/plain" can_multiple = True - def __init__(self, *args: Any, **kw: Any) -> None: - BaseTextFormatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + BaseTextFormatter.__init__(self, *args) def finish_output(self) -> None: "Fill in the template with RED's results." @@ -194,8 +192,8 @@ def format_uri(self, resource: HttpResource) -> str: class VerboseTextListFormatter(TextListFormatter): name = "txt_verbose" - def __init__(self, *args: Any, **kw: Any) -> None: - TextListFormatter.__init__(self, *args, **kw) + def __init__(self, *args: Unpack[FormatterArgs]) -> None: + TextListFormatter.__init__(self, *args) self.verbose = True diff --git a/redbot/webui/__init__.py b/redbot/webui/__init__.py index ff186ee0..78686a18 100644 --- a/redbot/webui/__init__.py +++ b/redbot/webui/__init__.py @@ -128,7 +128,9 @@ def __init__( self.config, HttpResource(self.config), self.output, - nonce=self.nonce, + { + "nonce": self.nonce, + }, ), b"405", b"Method Not Allowed", @@ -144,11 +146,13 @@ def run_test(self) -> None: self.config, top_resource, self.output, - allow_save=self.test_id, - is_saved=False, - test_id=self.test_id, - descend=self.descend, - nonce=self.nonce, + { + "allow_save": self.test_id, + "is_saved": False, + "test_id": self.test_id, + "descend": self.descend, + "nonce": self.nonce, + }, ) continue_test = partial(self.continue_test, top_resource, formatter) error_response = partial(self.error_response, formatter) @@ -281,8 +285,10 @@ def show_default(self) -> None: self.config, resource, self.output, - is_blank=self.test_uri == "", - nonce=self.nonce, + { + "is_blank": self.test_uri == "", + "nonce": self.nonce, + }, ) if self.check_name: formatter.resource = cast( diff --git a/redbot/webui/saved_tests.py b/redbot/webui/saved_tests.py index 8b953fec..cd0aab46 100644 --- a/redbot/webui/saved_tests.py +++ b/redbot/webui/saved_tests.py @@ -145,10 +145,12 @@ def load_saved_test(webui: "RedWebUi") -> None: webui.config, display_resource, webui.output, - allow_save=(not is_saved), - is_saved=True, - test_id=webui.test_id, - nonce=webui.nonce, + { + "allow_save": (not is_saved), + "is_saved": True, + "test_id": webui.test_id, + "nonce": webui.nonce, + }, ) webui.exchange.response_start( diff --git a/redbot/webui/slack.py b/redbot/webui/slack.py index 53f26fda..bf743aaf 100644 --- a/redbot/webui/slack.py +++ b/redbot/webui/slack.py @@ -21,12 +21,15 @@ def slack_run(webui: "RedWebUi") -> None: webui.test_uri = webui.body_args.get("text", [""])[0].strip() webui.test_id = init_save_file(webui) slack_response_uri = webui.body_args.get("response_url", [""])[0].strip() + resource = HttpResource(webui.config) formatter = slack.SlackFormatter( webui.config, - None, + resource, webui.output, - slack_uri=slack_response_uri, - test_id=webui.test_id, + { + "slack_uri": slack_response_uri, + "test_id": webui.test_id, + }, ) webui.exchange.response_start(