@@ -270,13 +270,28 @@ def start(self) -> None:
270270 self .playwright = sync_playwright ().start ()
271271
272272 # Build launch arguments
273+ #
274+ # NOTE: Prefer a single --disable-features=... flag; Chrome's behavior with
275+ # multiple flags is easy to get wrong (last-one-wins vs merge).
276+ #
277+ # - WebRtcHideLocalIpsWithMdns: WebRTC leak protection
278+ # - TranslateUI: reduce UI popups / noise in automation
279+ # - EnableTLS13EarlyData: avoid intermittent HTTP 425 "too early" responses
280+ # from some CDNs/origins when Chrome uses TLS 1.3 0-RTT early data.
281+ disabled_features = [
282+ "WebRtcHideLocalIpsWithMdns" ,
283+ "TranslateUI" ,
284+ "EnableTLS13EarlyData" ,
285+ ]
273286 args = [
274287 f"--disable-extensions-except={ self ._extension_path } " ,
275288 f"--load-extension={ self ._extension_path } " ,
276289 "--disable-blink-features=AutomationControlled" , # Hides 'navigator.webdriver'
277290 "--disable-infobars" ,
278- # WebRTC leak protection (prevents real IP exposure when using proxies/VPNs)
279- "--disable-features=WebRtcHideLocalIpsWithMdns" ,
291+ # HTTP/3 (QUIC) can surface intermittent edge/CDN weirdness in automation
292+ # (including minimal error pages like "too early"). Prefer stability.
293+ "--disable-quic" ,
294+ f"--disable-features={ ',' .join (disabled_features )} " ,
280295 "--force-webrtc-ip-handling-policy=disable_non_proxied_udp" ,
281296 ]
282297
@@ -302,7 +317,6 @@ def start(self) -> None:
302317 "--disable-background-timer-throttling" , # Disable background throttling
303318 "--disable-backgrounding-occluded-windows" , # Disable backgrounding
304319 "--disable-renderer-backgrounding" , # Disable renderer backgrounding
305- "--disable-features=TranslateUI" , # Disable translate UI
306320 "--disable-ipc-flooding-protection" , # Disable IPC flooding protection
307321 "--disable-logging" , # Disable logging to reduce stderr noise
308322 "--log-level=3" , # Set log level to fatal only (suppresses warnings)
@@ -902,12 +916,21 @@ async def start(self) -> None:
902916 self .playwright = await async_playwright ().start ()
903917
904918 # Build launch arguments
919+ #
920+ # NOTE: Prefer a single --disable-features=... flag; Chrome's behavior with
921+ # multiple flags is easy to get wrong (last-one-wins vs merge).
922+ disabled_features = [
923+ "WebRtcHideLocalIpsWithMdns" ,
924+ "TranslateUI" ,
925+ "EnableTLS13EarlyData" ,
926+ ]
905927 args = [
906928 f"--disable-extensions-except={ self ._extension_path } " ,
907929 f"--load-extension={ self ._extension_path } " ,
908930 "--disable-blink-features=AutomationControlled" ,
909931 "--disable-infobars" ,
910- "--disable-features=WebRtcHideLocalIpsWithMdns" ,
932+ "--disable-quic" ,
933+ f"--disable-features={ ',' .join (disabled_features )} " ,
911934 "--force-webrtc-ip-handling-policy=disable_non_proxied_udp" ,
912935 ]
913936
@@ -933,7 +956,6 @@ async def start(self) -> None:
933956 "--disable-background-timer-throttling" , # Disable background throttling
934957 "--disable-backgrounding-occluded-windows" , # Disable backgrounding
935958 "--disable-renderer-backgrounding" , # Disable renderer backgrounding
936- "--disable-features=TranslateUI" , # Disable translate UI
937959 "--disable-ipc-flooding-protection" , # Disable IPC flooding protection
938960 "--disable-logging" , # Disable logging to reduce stderr noise
939961 "--log-level=3" , # Set log level to fatal only (suppresses warnings)
0 commit comments