@@ -48,6 +48,19 @@ def __init__(self):
4848 self .extract = _AsyncExtractManager ()
4949
5050
51+ def _run_scrape_tool_sync (params : Mapping [str , object ]) -> None :
52+ client = _Client ()
53+ WebsiteScrapeTool .runnable (client , params )
54+
55+
56+ def _run_scrape_tool_async (params : Mapping [str , object ]) -> None :
57+ async def run () -> None :
58+ client = _AsyncClient ()
59+ await WebsiteScrapeTool .async_runnable (client , params )
60+
61+ asyncio .run (run ())
62+
63+
5164def test_tool_wrappers_accept_mapping_inputs ():
5265 client = _Client ()
5366 params = MappingProxyType ({"url" : "https://example.com" })
@@ -207,3 +220,86 @@ def __getitem__(self, key: str) -> object:
207220 WebsiteScrapeTool .runnable (client , _BrokenValueMapping ())
208221
209222 assert exc_info .value .original_error is None
223+
224+
225+ @pytest .mark .parametrize ("runner" , [_run_scrape_tool_sync , _run_scrape_tool_async ])
226+ def test_tool_wrappers_wrap_param_key_strip_failures (runner ):
227+ class _BrokenStripKey (str ):
228+ def strip (self , chars = None ): # type: ignore[override]
229+ _ = chars
230+ raise RuntimeError ("tool param key strip exploded" )
231+
232+ with pytest .raises (
233+ HyperbrowserError , match = "Failed to normalize tool param key"
234+ ) as exc_info :
235+ runner ({_BrokenStripKey ("url" ): "https://example.com" })
236+
237+ assert isinstance (exc_info .value .original_error , RuntimeError )
238+
239+
240+ @pytest .mark .parametrize ("runner" , [_run_scrape_tool_sync , _run_scrape_tool_async ])
241+ def test_tool_wrappers_preserve_hyperbrowser_param_key_strip_failures (runner ):
242+ class _BrokenStripKey (str ):
243+ def strip (self , chars = None ): # type: ignore[override]
244+ _ = chars
245+ raise HyperbrowserError ("custom tool param key strip failure" )
246+
247+ with pytest .raises (
248+ HyperbrowserError , match = "custom tool param key strip failure"
249+ ) as exc_info :
250+ runner ({_BrokenStripKey ("url" ): "https://example.com" })
251+
252+ assert exc_info .value .original_error is None
253+
254+
255+ @pytest .mark .parametrize ("runner" , [_run_scrape_tool_sync , _run_scrape_tool_async ])
256+ def test_tool_wrappers_wrap_non_string_param_key_strip_results (runner ):
257+ class _BrokenStripKey (str ):
258+ def strip (self , chars = None ): # type: ignore[override]
259+ _ = chars
260+ return object ()
261+
262+ with pytest .raises (
263+ HyperbrowserError , match = "Failed to normalize tool param key"
264+ ) as exc_info :
265+ runner ({_BrokenStripKey ("url" ): "https://example.com" })
266+
267+ assert isinstance (exc_info .value .original_error , TypeError )
268+
269+
270+ @pytest .mark .parametrize ("runner" , [_run_scrape_tool_sync , _run_scrape_tool_async ])
271+ def test_tool_wrappers_wrap_param_key_character_validation_failures (runner ):
272+ class _BrokenIterKey (str ):
273+ def strip (self , chars = None ): # type: ignore[override]
274+ _ = chars
275+ return self
276+
277+ def __iter__ (self ):
278+ raise RuntimeError ("tool param key iteration exploded" )
279+
280+ with pytest .raises (
281+ HyperbrowserError , match = "Failed to validate tool param key characters"
282+ ) as exc_info :
283+ runner ({_BrokenIterKey ("url" ): "https://example.com" })
284+
285+ assert isinstance (exc_info .value .original_error , RuntimeError )
286+
287+
288+ @pytest .mark .parametrize ("runner" , [_run_scrape_tool_sync , _run_scrape_tool_async ])
289+ def test_tool_wrappers_preserve_hyperbrowser_param_key_character_validation_failures (
290+ runner ,
291+ ):
292+ class _BrokenIterKey (str ):
293+ def strip (self , chars = None ): # type: ignore[override]
294+ _ = chars
295+ return self
296+
297+ def __iter__ (self ):
298+ raise HyperbrowserError ("custom tool param key iteration failure" )
299+
300+ with pytest .raises (
301+ HyperbrowserError , match = "custom tool param key iteration failure"
302+ ) as exc_info :
303+ runner ({_BrokenIterKey ("url" ): "https://example.com" })
304+
305+ assert exc_info .value .original_error is None
0 commit comments