From 90f9226c7cd259e76852b128adfcb9d1733528c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Skytt=C3=A4?= Date: Thu, 4 Nov 2021 23:24:35 +0200 Subject: [PATCH 1/4] Check docstrings with flake8-docstrings --- .pre-commit-config.yaml | 2 ++ setup.cfg | 3 ++- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 664f48f74d..31c701f0bb 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -79,6 +79,8 @@ repos: rev: '4.0.1' hooks: - id: flake8 + additional_dependencies: + - flake8-docstrings==1.6.0 exclude: "^docs/" - repo: git://github.com/Lucas-C/pre-commit-hooks-markup rev: v1.0.1 diff --git a/setup.cfg b/setup.cfg index 362f0073c0..88836c73fc 100644 --- a/setup.cfg +++ b/setup.cfg @@ -81,7 +81,8 @@ max-line-length=79 zip_ok = false [flake8] -ignore = N801,N802,N803,E203,E226,E305,W504,E252,E301,E302,E704,W503,W504,F811 +# TODO: don't disable D*, fix up issues instead +ignore = N801,N802,N803,E203,E226,E305,W504,E252,E301,E302,E704,W503,W504,F811,D1,D200,D202,D205,D209,D4 max-line-length = 88 [isort] From 962b573780d85ed120e0f3d68a1fafe867f72cd0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Skytt=C3=A4?= Date: Mon, 8 Nov 2021 22:12:17 +0200 Subject: [PATCH 2/4] Address pydocstyle D2xx issues --- aiohttp/client.py | 18 +++++----- aiohttp/client_exceptions.py | 3 +- aiohttp/connector.py | 19 +++++----- aiohttp/formdata.py | 6 ++-- aiohttp/helpers.py | 11 +++--- aiohttp/http_parser.py | 7 ++-- aiohttp/locks.py | 5 +-- aiohttp/multipart.py | 34 +++++++++--------- aiohttp/pytest_plugin.py | 21 ++++++----- aiohttp/resolver.py | 6 ++-- aiohttp/streams.py | 15 ++++---- aiohttp/test_utils.py | 20 ++++------- aiohttp/tracing.py | 10 +++--- aiohttp/web_middlewares.py | 6 ++-- aiohttp/web_protocol.py | 30 +++++++++------- aiohttp/web_request.py | 3 +- aiohttp/web_urldispatcher.py | 41 ++++++++-------------- examples/web_classview.py | 3 +- examples/web_cookies.py | 3 +- examples/web_rewrite_headers_middleware.py | 5 ++- examples/web_srv.py | 3 +- examples/web_srv_route_deco.py | 4 +-- examples/web_srv_route_table.py | 4 +-- examples/web_ws.py | 3 +- setup.cfg | 2 +- tests/test___all__.py | 4 +-- tests/test_http_parser.py | 3 +- 27 files changed, 137 insertions(+), 152 deletions(-) diff --git a/aiohttp/client.py b/aiohttp/client.py index 6e5125cfe5..4ba3c033a9 100644 --- a/aiohttp/client.py +++ b/aiohttp/client.py @@ -1032,23 +1032,21 @@ def connector_owner(self) -> bool: def raise_for_status( self, ) -> Union[bool, Callable[[ClientResponse], Awaitable[None]]]: - """ - Should `ClientResponse.raise_for_status()` - be called for each response - """ + """Should `ClientResponse.raise_for_status()` be called for each response.""" return self._raise_for_status @property def auto_decompress(self) -> bool: - """Should the body response be automatically decompressed""" + """Should the body response be automatically decompressed.""" return self._auto_decompress @property def trust_env(self) -> bool: """ - Should get proxies information - from HTTP_PROXY / HTTPS_PROXY environment variables - or ~/.netrc file if present + Should proxies information from environment or netrc be trusted. + + Information is from HTTP_PROXY / HTTPS_PROXY environment variables + or ~/.netrc file if present. """ return self._trust_env @@ -1191,7 +1189,9 @@ def request( connector: Optional[BaseConnector] = None, read_bufsize: Optional[int] = None, ) -> _SessionRequestContextManager: - """Constructs and sends a request. Returns response object. + """Constructs and sends a request. + + Returns response object. method - HTTP method url - request url params - (optional) Dictionary or bytes to be sent in the query diff --git a/aiohttp/client_exceptions.py b/aiohttp/client_exceptions.py index 5f2f8958e8..a41dbfd1b1 100644 --- a/aiohttp/client_exceptions.py +++ b/aiohttp/client_exceptions.py @@ -229,7 +229,8 @@ class InvalidURL(ClientError, ValueError): """Invalid URL. URL used for fetching is malformed, e.g. it doesn't contains host - part.""" + part. + """ # Derive from ValueError for backward compatibility diff --git a/aiohttp/connector.py b/aiohttp/connector.py index f1cae659f5..2ebb464152 100644 --- a/aiohttp/connector.py +++ b/aiohttp/connector.py @@ -281,12 +281,10 @@ def limit(self) -> int: @property def limit_per_host(self) -> int: - """The limit_per_host for simultaneous connections - to the same endpoint. + """The limit for simultaneous connections to the same endpoint. Endpoints are the same if they are have equal (host, port, is_ssl) triple. - """ return self._limit_per_host @@ -344,6 +342,7 @@ def _drop_acquired_per_host( def _cleanup_closed(self) -> None: """Double confirmation for transport close. + Some broken ssl servers may leave socket open without proper close. """ if self._cleanup_closed_handle: @@ -424,13 +423,13 @@ def closed(self) -> bool: def _available_connections(self, key: "ConnectionKey") -> int: """ - Return number of available connections taking into account - the limit, limit_per_host and the connection key. + Return number of available connections. - If it returns less than 1 means that there is no connections - availables. - """ + The limit, limit_per_host and the connection key are taken into account. + If it returns less than 1 means that there are no connections + available. + """ if self._limit: # total calc available connections available = self._limit - len(self._acquired) @@ -571,7 +570,9 @@ def _get(self, key: "ConnectionKey") -> Optional[ResponseHandler]: def _release_waiter(self) -> None: """ - Iterates over all waiters till found one that is not finsihed and + Iterates over all waiters until one to be released is found. + + The one to be released is not finsihed and belongs to a host that has available connections. """ if not self._waiters: diff --git a/aiohttp/formdata.py b/aiohttp/formdata.py index 8d0d89f78f..ff3869e8a4 100644 --- a/aiohttp/formdata.py +++ b/aiohttp/formdata.py @@ -12,8 +12,10 @@ class FormData: - """Helper class for multipart/form-data and - application/x-www-form-urlencoded body generation.""" + """Helper class for form body generation. + + Supports multipart/form-data and application/x-www-form-urlencoded. + """ def __init__( self, diff --git a/aiohttp/helpers.py b/aiohttp/helpers.py index 77eaf8c355..b9853b1829 100644 --- a/aiohttp/helpers.py +++ b/aiohttp/helpers.py @@ -197,7 +197,9 @@ def strip_auth_from_url(url: URL) -> Tuple[URL, Optional[BasicAuth]]: def netrc_from_env() -> Optional[netrc.netrc]: - """Attempt to load the netrc file from the path specified by the env-var + """Load netrc from file. + + Attempt to load it from the path specified by the env-var NETRC or in the default location in the user's home directory. Returns None if it couldn't be found or fails to parse. @@ -425,7 +427,6 @@ def is_expected_content_type( ) -> bool: """Checks if received content type is processable as an expected one. - Both arguments should be given without parameters. """ if expected_content_type == "application/json": @@ -438,12 +439,13 @@ class _TSelf(Protocol, Generic[_T]): class reify(Generic[_T]): - """Use as a class method decorator. It operates almost exactly like + """Use as a class method decorator. + + It operates almost exactly like the Python `@property` decorator, but it puts the result of the method it decorates into the instance dict after the first call, effectively replacing the function it decorates with an instance variable. It is, in Python parlance, a data descriptor. - """ def __init__(self, wrapped: Callable[..., _T]) -> None: @@ -851,7 +853,6 @@ def set_cookie( Sets new cookie or updates existent with new value. Also updates only those params which are not None. """ - old = self._cookies.get(name) if old is not None and old.coded_value == "": # deleted cookie diff --git a/aiohttp/http_parser.py b/aiohttp/http_parser.py index ccf421c617..3824276f0a 100644 --- a/aiohttp/http_parser.py +++ b/aiohttp/http_parser.py @@ -512,7 +512,9 @@ def set_upgraded(self, val: bool) -> None: class HttpRequestParser(HttpParser[RawRequestMessage]): - """Read request status line. Exception .http_exceptions.BadStatusLine + """Read request status line. + + Exception .http_exceptions.BadStatusLine could be raised in case of any errors in status line. Returns RawRequestMessage. """ @@ -590,7 +592,8 @@ class HttpResponseParser(HttpParser[RawResponseMessage]): """Read response status line and headers. BadStatusLine could be raised in case of any errors in status line. - Returns RawResponseMessage""" + Returns RawResponseMessage. + """ def parse_message(self, lines: List[bytes]) -> RawResponseMessage: line = lines[0].decode("utf-8", "surrogateescape") diff --git a/aiohttp/locks.py b/aiohttp/locks.py index 8ea99d70ce..1aaba0741d 100644 --- a/aiohttp/locks.py +++ b/aiohttp/locks.py @@ -9,8 +9,9 @@ class EventResultOrError: - """ - This class wrappers the Event asyncio lock allowing either awake the + """Event asyncio lock helper class. + + Wraps the Event asyncio lock allowing either to awake the locked Tasks without any error or raising an exception. thanks to @vorpalsmith for the simple design. diff --git a/aiohttp/multipart.py b/aiohttp/multipart.py index 7fe1136c28..9cd3db4e4b 100644 --- a/aiohttp/multipart.py +++ b/aiohttp/multipart.py @@ -242,8 +242,10 @@ async def next( return item async def release(self) -> None: - """Releases the connection gracefully, reading all the content - to the void.""" + """Release the connection gracefully. + + All remaining content is read to the void. + """ await self.resp.release() @@ -453,9 +455,7 @@ async def json(self, *, encoding: Optional[str] = None) -> Optional[Dict[str, An return cast(Dict[str, Any], json.loads(data.decode(encoding))) async def form(self, *, encoding: Optional[str] = None) -> List[Tuple[str, str]]: - """Like read(), but assumes that body parts contains form - urlencoded data. - """ + """Like read(), but assumes that body parts contain form urlencoded data.""" data = await self.read(decode=True) if not data: return [] @@ -474,7 +474,9 @@ def at_eof(self) -> bool: return self._at_eof def decode(self, data: bytes) -> bytes: - """Decodes data according the specified Content-Encoding + """Decodes data. + + Decoding is done according the specified Content-Encoding or Content-Transfer-Encoding headers value. """ if CONTENT_TRANSFER_ENCODING in self.headers: @@ -517,17 +519,18 @@ def get_charset(self, default: str) -> str: @reify def name(self) -> Optional[str]: - """Returns name specified in Content-Disposition header or None - if missed or header is malformed. - """ + """Returns name specified in Content-Disposition header. + If the header is missing or malformed, returns None. + """ _, params = parse_content_disposition(self.headers.get(CONTENT_DISPOSITION)) return content_disposition_filename(params, "name") @reify def filename(self) -> Optional[str]: - """Returns filename specified in Content-Disposition header or None - if missed or header is malformed. + """Returns filename specified in Content-Disposition header. + + Returns None if the header is missing or malformed. """ _, params = parse_content_disposition(self.headers.get(CONTENT_DISPOSITION)) return content_disposition_filename(params, "filename") @@ -612,9 +615,7 @@ def from_response( return obj def at_eof(self) -> bool: - """Returns True if the final boundary was reached or - False otherwise. - """ + """Returns True if the final boundary was reached, false otherwise.""" return self._at_eof async def next( @@ -654,8 +655,9 @@ def _get_part_reader( self, headers: "CIMultiDictProxy[str]", ) -> Union["MultipartReader", BodyPartReader]: - """Dispatches the response by the `Content-Type` header, returning - suitable reader instance. + """Dispatches the response by the `Content-Type` header. + + Returns a suitable reader instance. :param dict headers: Response headers """ diff --git a/aiohttp/pytest_plugin.py b/aiohttp/pytest_plugin.py index 153db35276..d08327e031 100644 --- a/aiohttp/pytest_plugin.py +++ b/aiohttp/pytest_plugin.py @@ -54,7 +54,8 @@ def pytest_addoption(parser): # type: ignore[no-untyped-def] def pytest_fixture_setup(fixturedef): # type: ignore[no-untyped-def] - """ + """Set up pytest fixture. + Allow fixtures to be coroutines. Run coroutine fixtures in an event loop. """ func = fixturedef.func @@ -123,8 +124,9 @@ def loop_debug(request): # type: ignore[no-untyped-def] @contextlib.contextmanager def _runtime_warning_context(): # type: ignore[no-untyped-def] - """ - Context manager which checks for RuntimeWarnings, specifically to + """Context manager which checks for RuntimeWarnings. + + This exists specifically to avoid "coroutine 'X' was never awaited" warnings being missed. If RuntimeWarnings occur in the context a RuntimeError is raised. @@ -152,8 +154,9 @@ def _runtime_warning_context(): # type: ignore[no-untyped-def] @contextlib.contextmanager def _passthrough_loop_context(loop, fast=False): # type: ignore[no-untyped-def] - """ - setups and tears down a loop unless one is passed in via the loop + """Passthrough loop context. + + Sets up and tears down a loop unless one is passed in via the loop argument when it's passed straight through. """ if loop: @@ -167,17 +170,13 @@ def _passthrough_loop_context(loop, fast=False): # type: ignore[no-untyped-def] def pytest_pycollect_makeitem(collector, name, obj): # type: ignore[no-untyped-def] - """ - Fix pytest collecting for coroutines. - """ + """Fix pytest collecting for coroutines.""" if collector.funcnamefilter(name) and asyncio.iscoroutinefunction(obj): return list(collector._genfunctions(name, obj)) def pytest_pyfunc_call(pyfuncitem): # type: ignore[no-untyped-def] - """ - Run coroutines in an event loop instead of a normal function call. - """ + """Run coroutines in an event loop instead of a normal function call.""" fast = pyfuncitem.config.getoption("--aiohttp-fast") if asyncio.iscoroutinefunction(pyfuncitem.function): existing_loop = pyfuncitem.funcargs.get( diff --git a/aiohttp/resolver.py b/aiohttp/resolver.py index e222001082..66a49731fe 100644 --- a/aiohttp/resolver.py +++ b/aiohttp/resolver.py @@ -17,8 +17,10 @@ class ThreadedResolver(AbstractResolver): - """Use Executor for synchronous getaddrinfo() calls, which defaults to - concurrent.futures.ThreadPoolExecutor. + """Threaded resolver. + + Uses an Executor for synchronous getaddrinfo() calls. + concurrent.futures.ThreadPoolExecutor is used by default. """ def __init__(self) -> None: diff --git a/aiohttp/streams.py b/aiohttp/streams.py index 185f46ecda..5dc7308b65 100644 --- a/aiohttp/streams.py +++ b/aiohttp/streams.py @@ -74,16 +74,16 @@ def iter_chunked(self, n: int) -> AsyncStreamIterator[bytes]: ) def iter_any(self) -> AsyncStreamIterator[bytes]: - """Returns an asynchronous iterator that yields all the available - data as soon as it is received + """Yield all available data as soon as it is received. Python-3.5 available for Python 3.5+ only """ return AsyncStreamIterator(self.readany) # type: ignore[attr-defined] def iter_chunks(self) -> ChunkTupleAsyncStreamIterator: - """Returns an asynchronous iterator that yields chunks of data - as they are received by the server. The yielded objects are tuples + """Yield chunks of data as they are received by the server. + + The yielded objects are tuples of (bytes, bool) as returned by the StreamReader.readchunk method. Python-3.5 available for Python 3.5+ only @@ -391,7 +391,9 @@ async def readany(self) -> bytes: return self._read_nowait(-1) async def readchunk(self) -> Tuple[bytes, bool]: - """Returns a tuple of (data, end_of_http_chunk). When chunked transfer + """Returns a tuple of (data, end_of_http_chunk). + + When chunked transfer encoding is used, end_of_http_chunk is a boolean indicating if the end of the data corresponds to the end of a HTTP chunk , otherwise it is always False. @@ -625,7 +627,8 @@ def __aiter__(self) -> AsyncStreamIterator[_T]: class FlowControlDataQueue(DataQueue[_T]): """FlowControlDataQueue resumes and pauses an underlying stream. - It is a destination for parsed data.""" + It is a destination for parsed data. + """ def __init__( self, protocol: BaseProtocol, limit: int, *, loop: asyncio.AbstractEventLoop diff --git a/aiohttp/test_utils.py b/aiohttp/test_utils.py index 4a157c5cac..956ad78665 100644 --- a/aiohttp/test_utils.py +++ b/aiohttp/test_utils.py @@ -399,8 +399,7 @@ async def __aexit__( class AioHTTPTestCase(TestCase): - """A base class to allow for unittest web applications using - aiohttp. + """A base class to allow for unittest web applications using aiohttp. Provides the following: @@ -415,19 +414,18 @@ class AioHTTPTestCase(TestCase): """ async def get_application(self) -> Application: - """ + """Get application. + This method should be overridden to return the aiohttp.web.Application object to test. - """ return self.get_app() def get_app(self) -> Application: """Obsolete method used to constructing web application. - Use .get_application() coroutine instead - + Use .get_application() coroutine instead. """ raise RuntimeError("Did you forget to define get_application()?") @@ -480,8 +478,7 @@ def loop_context( def setup_test_loop( loop_factory: _LOOP_FACTORY = asyncio.new_event_loop, ) -> asyncio.AbstractEventLoop: - """Create and return an asyncio.BaseEventLoop - instance. + """Create and return an asyncio.BaseEventLoop instance. The caller should also call teardown_test_loop, once they are done with the loop. @@ -513,10 +510,7 @@ def setup_test_loop( def teardown_test_loop(loop: asyncio.AbstractEventLoop, fast: bool = False) -> None: - """Teardown and cleanup an event_loop created - by setup_test_loop. - - """ + """Teardown and cleanup an event_loop created by setup_test_loop.""" closed = loop.is_closed() if not closed: loop.call_soon(loop.stop) @@ -580,9 +574,7 @@ def make_mocked_request( Useful in unit tests, when spinning full web server is overkill or specific conditions and errors are hard to trigger. - """ - task = mock.Mock() if loop is ...: loop = mock.Mock() diff --git a/aiohttp/tracing.py b/aiohttp/tracing.py index 7ffe93f850..c6c99d6ed2 100644 --- a/aiohttp/tracing.py +++ b/aiohttp/tracing.py @@ -47,8 +47,7 @@ def __call__( class TraceConfig: - """First-class used to trace requests launched via ClientSession - objects.""" + """First-class used to trace requests launched via ClientSession objects.""" def __init__( self, trace_config_ctx_factory: Type[SimpleNamespace] = SimpleNamespace @@ -337,8 +336,11 @@ class TraceRequestHeadersSentParams: class Trace: - """Internal class used to keep together the main dependencies used - at the moment of send a signal.""" + """Internal dependency holder class. + + Used to keep together the main dependencies used + at the moment of send a signal. + """ def __init__( self, diff --git a/aiohttp/web_middlewares.py b/aiohttp/web_middlewares.py index d3baf609dd..4583824458 100644 --- a/aiohttp/web_middlewares.py +++ b/aiohttp/web_middlewares.py @@ -49,10 +49,9 @@ def normalize_path_middleware( merge_slashes: bool = True, redirect_class: Type[HTTPMove] = HTTPPermanentRedirect, ) -> Middleware: - """ - Middleware factory which produces a middleware that normalizes - the path of a request. By normalizing it means: + """Factory for producing a middleware that normalizes the path of a request. + Normalizing means: - Add or remove a trailing slash to the path. - Double slashes are replaced by one. @@ -78,7 +77,6 @@ def normalize_path_middleware( If merge_slashes is True, merge multiple consecutive slashes in the path into one. """ - correct_configuration = not (append_slash and remove_slash) assert correct_configuration, "Cannot both remove and append slash" diff --git a/aiohttp/web_protocol.py b/aiohttp/web_protocol.py index fb9f363e3b..6a775cf38e 100644 --- a/aiohttp/web_protocol.py +++ b/aiohttp/web_protocol.py @@ -87,10 +87,7 @@ class PayloadAccessError(Exception): class AccessLoggerWrapper(AbstractAsyncAccessLogger): - """ - Wraps an AbstractAccessLogger so it behaves - like an AbstractAsyncAccessLogger. - """ + """Wrap an AbstractAccessLogger so it behaves like an AbstractAsyncAccessLogger.""" def __init__( self, access_logger: AbstractAccessLogger, loop: asyncio.AbstractEventLoop @@ -261,9 +258,11 @@ def keepalive_timeout(self) -> float: return self._keepalive_timeout async def shutdown(self, timeout: Optional[float] = 15.0) -> None: - """Worker process is about to exit, we need cleanup everything and - stop accepting requests. It is especially important for keep-alive - connections.""" + """Do worker process exit preparations. + + We need to clean up everything and stop accepting requests. + It is especially important for keep-alive connections. + """ self._force_close = True if self._keepalive_handle is not None: @@ -395,14 +394,17 @@ def keep_alive(self, val: bool) -> None: self._keepalive_handle = None def close(self) -> None: - """Stop accepting new pipelining messages and close - connection when handlers done processing messages""" + """Close connection. + + Stop accepting new pipelining messages and close + connection when handlers done processing messages. + """ self._close = True if self._waiter: self._waiter.cancel() def force_close(self) -> None: - """Force close connection""" + """Forcefully close connection.""" self._force_close = True if self._waiter: self._waiter.cancel() @@ -598,8 +600,9 @@ async def start(self) -> None: async def finish_response( self, request: BaseRequest, resp: StreamResponse, start_time: float ) -> bool: - """ - Prepare the response and write_eof, then log access. This has to + """Prepare the response and write_eof, then log access. + + This has to be called within the context of any exception so the access logger can get exception information. Returns True if the client disconnects prematurely. @@ -642,7 +645,8 @@ def handle_error( """Handle errors. Returns HTTP response with specific status code. Logs additional - information. It always closes current connection.""" + information. It always closes current connection. + """ self.log_exception("Error handling request", exc_info=exc) # some data already got sent, connection is broken diff --git a/aiohttp/web_request.py b/aiohttp/web_request.py index b47737a89b..8279c67f7c 100644 --- a/aiohttp/web_request.py +++ b/aiohttp/web_request.py @@ -211,9 +211,7 @@ def clone( Creates and returns a new instance of Request object. If no parameters are given, an exact copy is returned. If a parameter is not passed, it will reuse the one from the current request object. - """ - if self._read_bytes: raise RuntimeError("Cannot clone request " "after reading its content") @@ -449,6 +447,7 @@ def path_qs(self) -> str: @reify def raw_path(self) -> str: """The URL including raw *PATH INFO* without the host or scheme. + Warning, the path is unquoted and may contains non valid URL characters E.g., ``/my%2Fpath%7Cwith%21some%25strange%24characters`` diff --git a/aiohttp/web_urldispatcher.py b/aiohttp/web_urldispatcher.py index a691661d7d..f014a7f924 100644 --- a/aiohttp/web_urldispatcher.py +++ b/aiohttp/web_urldispatcher.py @@ -127,16 +127,16 @@ def url_for(self, **kwargs: str) -> URL: @abc.abstractmethod # pragma: no branch async def resolve(self, request: Request) -> _Resolve: - """Resolve resource + """Resolve resource. - Return (UrlMappingMatchInfo, allowed_methods) pair.""" + Return (UrlMappingMatchInfo, allowed_methods) pair. + """ @abc.abstractmethod def add_prefix(self, prefix: str) -> None: """Add a prefix to processed URLs. Required for subapplications support. - """ @abc.abstractmethod @@ -1117,15 +1117,11 @@ def add_static( return resource def add_head(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method HEAD - """ + """Shortcut for add_route with method HEAD.""" return self.add_route(hdrs.METH_HEAD, path, handler, **kwargs) def add_options(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method OPTIONS - """ + """Shortcut for add_route with method OPTIONS.""" return self.add_route(hdrs.METH_OPTIONS, path, handler, **kwargs) def add_get( @@ -1137,9 +1133,10 @@ def add_get( allow_head: bool = True, **kwargs: Any, ) -> AbstractRoute: - """ - Shortcut for add_route with method GET, if allow_head is true another - route is added allowing head requests to the same endpoint + """Shortcut for add_route with method GET. + + If allow_head is true, another + route is added allowing head requests to the same endpoint. """ resource = self.add_resource(path, name=name) if allow_head: @@ -1147,35 +1144,25 @@ def add_get( return resource.add_route(hdrs.METH_GET, handler, **kwargs) def add_post(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method POST - """ + """Shortcut for add_route with method POST.""" return self.add_route(hdrs.METH_POST, path, handler, **kwargs) def add_put(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method PUT - """ + """Shortcut for add_route with method PUT.""" return self.add_route(hdrs.METH_PUT, path, handler, **kwargs) def add_patch(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method PATCH - """ + """Shortcut for add_route with method PATCH.""" return self.add_route(hdrs.METH_PATCH, path, handler, **kwargs) def add_delete(self, path: str, handler: Handler, **kwargs: Any) -> AbstractRoute: - """ - Shortcut for add_route with method DELETE - """ + """Shortcut for add_route with method DELETE.""" return self.add_route(hdrs.METH_DELETE, path, handler, **kwargs) def add_view( self, path: str, handler: Type[AbstractView], **kwargs: Any ) -> AbstractRoute: - """ - Shortcut for add_route with ANY methods for a class-based view - """ + """Shortcut for add_route with ANY methods for a class-based view.""" return self.add_route(hdrs.METH_ANY, path, handler, **kwargs) def freeze(self) -> None: diff --git a/examples/web_classview.py b/examples/web_classview.py index fc3fe67b85..fc90b6d852 100755 --- a/examples/web_classview.py +++ b/examples/web_classview.py @@ -1,6 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web class based views -""" +"""Example for aiohttp.web class based views.""" import functools import json diff --git a/examples/web_cookies.py b/examples/web_cookies.py index 6836569183..0130dd8ab2 100755 --- a/examples/web_cookies.py +++ b/examples/web_cookies.py @@ -1,6 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web basic server with cookies. -""" +"""Example for aiohttp.web basic server with cookies.""" from pprint import pformat from typing import NoReturn diff --git a/examples/web_rewrite_headers_middleware.py b/examples/web_rewrite_headers_middleware.py index 149dc28285..35c662974d 100755 --- a/examples/web_rewrite_headers_middleware.py +++ b/examples/web_rewrite_headers_middleware.py @@ -1,7 +1,6 @@ #!/usr/bin/env python3 -""" -Example for rewriting response headers by middleware. -""" +"""Example for rewriting response headers by middleware.""" + from aiohttp import web from aiohttp.typedefs import Handler diff --git a/examples/web_srv.py b/examples/web_srv.py index b87f6c43ba..37b44aad14 100755 --- a/examples/web_srv.py +++ b/examples/web_srv.py @@ -1,6 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web basic server -""" +"""Example for aiohttp.web basic server.""" import textwrap diff --git a/examples/web_srv_route_deco.py b/examples/web_srv_route_deco.py index 65a4f8618b..78d25441d3 100644 --- a/examples/web_srv_route_deco.py +++ b/examples/web_srv_route_deco.py @@ -1,7 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web basic server -with decorator definition for routes -""" +"""Example for aiohttp.web basic server with decorator definition for routes.""" import textwrap diff --git a/examples/web_srv_route_table.py b/examples/web_srv_route_table.py index 4d1acc43c5..7f3b19e002 100644 --- a/examples/web_srv_route_table.py +++ b/examples/web_srv_route_table.py @@ -1,7 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web basic server -with table definition for routes -""" +"""Example for aiohttp.web basic server with table definition for routes.""" import textwrap diff --git a/examples/web_ws.py b/examples/web_ws.py index 24610f09bf..dbfb7f2d32 100755 --- a/examples/web_ws.py +++ b/examples/web_ws.py @@ -1,6 +1,5 @@ #!/usr/bin/env python3 -"""Example for aiohttp.web websocket server -""" +"""Example for aiohttp.web websocket server.""" import os from typing import Union diff --git a/setup.cfg b/setup.cfg index 88836c73fc..b007f59261 100644 --- a/setup.cfg +++ b/setup.cfg @@ -82,7 +82,7 @@ zip_ok = false [flake8] # TODO: don't disable D*, fix up issues instead -ignore = N801,N802,N803,E203,E226,E305,W504,E252,E301,E302,E704,W503,W504,F811,D1,D200,D202,D205,D209,D4 +ignore = N801,N802,N803,E203,E226,E305,W504,E252,E301,E302,E704,W503,W504,F811,D1,D4 max-line-length = 88 [isort] diff --git a/tests/test___all__.py b/tests/test___all__.py index d5e6445f9c..6c7d855e59 100644 --- a/tests/test___all__.py +++ b/tests/test___all__.py @@ -2,9 +2,7 @@ def test___all__(pytester: Any) -> None: - """ - See https://github.com/aio-libs/aiohttp/issues/6197 - """ + """See https://github.com/aio-libs/aiohttp/issues/6197""" pytester.makepyfile( test_a=""" from aiohttp import * diff --git a/tests/test_http_parser.py b/tests/test_http_parser.py index 2d5ae61e8e..c58abd4c55 100644 --- a/tests/test_http_parser.py +++ b/tests/test_http_parser.py @@ -1007,8 +1007,7 @@ async def test_http_payload_parser_deflate(self, stream: Any) -> None: assert out.is_eof() async def test_http_payload_parser_deflate_no_hdrs(self, stream: Any) -> None: - """Tests incorrectly formed data (no zlib headers)""" - + """Tests incorrectly formed data (no zlib headers).""" # c=compressobj(wbits=-15); b''.join([c.compress(b'data'), c.flush()]) COMPRESSED = b"KI,I\x04\x00" From 48b1a03b38a7b0b60d5a14d2d7f198bd33e9c1dc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Skytt=C3=A4?= Date: Mon, 8 Nov 2021 22:19:02 +0200 Subject: [PATCH 3/4] Add CHANGES entry --- CHANGES/6276.doc | 1 + 1 file changed, 1 insertion(+) create mode 100644 CHANGES/6276.doc diff --git a/CHANGES/6276.doc b/CHANGES/6276.doc new file mode 100644 index 0000000000..bfd0697149 --- /dev/null +++ b/CHANGES/6276.doc @@ -0,0 +1 @@ +Add flake8-docstrings to flake8 configuration, enable subset of checks. From d6fde5a0ce73b6dd9157820da4d67f10854445ad Mon Sep 17 00:00:00 2001 From: Andrew Svetlov Date: Thu, 11 Nov 2021 09:06:05 +0200 Subject: [PATCH 4/4] Fix linter --- docs/spelling_wordlist.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/spelling_wordlist.txt b/docs/spelling_wordlist.txt index f337fb95ca..493dc86528 100644 --- a/docs/spelling_wordlist.txt +++ b/docs/spelling_wordlist.txt @@ -154,6 +154,7 @@ dict django dns docstring +docstrings elasticsearch encodings env