refactor: Making all the codebase acceptable by PyRight

Also fixes #97
This commit is contained in:
Karim shoair
2025-10-05 04:03:39 +03:00
parent e149c715dd
commit debe03256b
21 changed files with 306 additions and 205 deletions
+6 -4
View File
@@ -58,7 +58,8 @@ class ResponseFactory:
"encoding": cls.__extract_browser_encoding(
current_response.headers.get("content-type", "")
)
or "utf-8",
if current_response
else "utf-8",
"cookies": tuple(),
"headers": current_response.all_headers() if current_response else {},
"request_headers": current_request.all_headers(),
@@ -161,7 +162,8 @@ class ResponseFactory:
"encoding": cls.__extract_browser_encoding(
current_response.headers.get("content-type", "")
)
or "utf-8",
if current_response
else "utf-8",
"cookies": tuple(),
"headers": await current_response.all_headers() if current_response else {},
"request_headers": await current_request.all_headers(),
@@ -255,8 +257,8 @@ class ResponseFactory:
"encoding": response.encoding or "utf-8",
"cookies": dict(response.cookies),
"headers": dict(response.headers),
"request_headers": dict(response.request.headers),
"method": response.request.method,
"request_headers": dict(response.request.headers) if response.request else {},
"method": response.request.method if response.request else "GET",
"history": response.history, # https://github.com/lexiforest/curl_cffi/issues/82
**parser_arguments,
}
+6 -9
View File
@@ -8,6 +8,7 @@ from scrapling.core.utils import log
from scrapling.core._types import (
Any,
Dict,
cast,
List,
Optional,
Tuple,
@@ -30,10 +31,10 @@ class Response(Selector):
request_headers: Dict,
encoding: str = "utf-8",
method: str = "GET",
history: List = None,
**selector_config: Dict,
history: List | None = None,
**selector_config: Any,
):
adaptive_domain = selector_config.pop("adaptive_domain", None)
adaptive_domain: str = cast(str, selector_config.pop("adaptive_domain", ""))
self.status = status
self.reason = reason
self.cookies = cookies
@@ -58,7 +59,7 @@ class BaseFetcher:
keep_cdata: Optional[bool] = False
storage_args: Optional[Dict] = None
keep_comments: Optional[bool] = False
adaptive_domain: Optional[str] = None
adaptive_domain: str = ""
parser_keywords: Tuple = (
"huge_tree",
"adaptive",
@@ -124,12 +125,8 @@ class BaseFetcher:
adaptive=cls.adaptive,
storage=cls.storage,
storage_args=cls.storage_args,
adaptive_domain=cls.adaptive_domain,
)
if cls.adaptive_domain:
if not isinstance(cls.adaptive_domain, str):
log.warning('[Ignored] The argument "adaptive_domain" must be of string type')
else:
parser_arguments.update({"adaptive_domain": cls.adaptive_domain})
return parser_arguments
+17 -10
View File
@@ -8,9 +8,10 @@ from platform import system as platform_system
from tldextract import extract
from browserforge.headers import Browser, HeaderGenerator
from scrapling.core._types import Dict, Optional
from scrapling.core._types import Dict, Literal
__OS_NAME__ = platform_system()
OSName = Literal["linux", "macos", "windows"]
@lru_cache(10, typed=True)
@@ -28,16 +29,20 @@ def generate_convincing_referer(url: str) -> str:
@lru_cache(1, typed=True)
def get_os_name() -> Optional[str]:
"""Get the current OS name in the same format needed for browserforge
def get_os_name() -> OSName | None:
"""Get the current OS name in the same format needed for browserforge, if the OS is Unknown, return None so browserforge uses all.
:return: Current OS name or `None` otherwise
"""
return {
"Linux": "linux",
"Darwin": "macos",
"Windows": "windows",
}.get(__OS_NAME__)
match __OS_NAME__:
case "Linux":
return "linux"
case "Darwin":
return "macos"
case "Windows":
return "windows"
case _:
return None
def generate_headers(browser_mode: bool = False) -> Dict:
@@ -58,8 +63,10 @@ def generate_headers(browser_mode: bool = False) -> Dict:
Browser(name="edge", min_version=130),
]
)
return HeaderGenerator(browser=browsers, os=os_name, device="desktop").generate()
if os_name:
return HeaderGenerator(browser=browsers, os=os_name, device="desktop").generate()
else:
return HeaderGenerator(browser=browsers, device="desktop").generate()
__default_useragent__ = generate_headers(browser_mode=False).get("User-Agent")
+11 -3
View File
@@ -11,7 +11,7 @@ from msgspec import Struct, structs, convert, ValidationError
from playwright.sync_api import Route
from scrapling.core.utils import log
from scrapling.core._types import Dict, Optional, Tuple
from scrapling.core._types import Dict, Tuple, overload, Literal
from scrapling.engines.constants import DEFAULT_DISABLED_RESOURCES
__BYPASSES_DIR__ = Path(__file__).parent / "bypasses"
@@ -49,7 +49,15 @@ async def async_intercept_route(route: async_Route):
await route.continue_()
def construct_proxy_dict(proxy_string: str | Dict[str, str], as_tuple=False) -> Optional[Dict | Tuple]:
@overload
def construct_proxy_dict(proxy_string: str | Dict[str, str] | Tuple, as_tuple: Literal[True]) -> Tuple: ...
@overload
def construct_proxy_dict(proxy_string: str | Dict[str, str] | Tuple, as_tuple: Literal[False] = False) -> Dict: ...
def construct_proxy_dict(proxy_string: str | Dict[str, str] | Tuple, as_tuple: bool = False) -> Dict | Tuple:
"""Validate a proxy and return it in the acceptable format for Playwright
Reference: https://playwright.dev/python/docs/network#http-proxy
@@ -83,7 +91,7 @@ def construct_proxy_dict(proxy_string: str | Dict[str, str], as_tuple=False) ->
except ValidationError as e:
raise TypeError(f"Invalid proxy dictionary: {e}")
return None
raise TypeError(f"Invalid proxy string: {proxy_string}")
@lru_cache(10, typed=True)