diff --git a/README.md b/README.md index 076a107..c80efaf 100644 --- a/README.md +++ b/README.md @@ -60,6 +60,7 @@ uvicorn.run(app) # view url with your browser # http://127.0.0.1:8000/chrome/screenshot?url=http://bing.com # http://127.0.0.1:8000/chrome/download?url=http://bing.com +# http://127.0.0.1:8000/chrome/js?url=http://bing.com&js=document.title ``` ### Client diff --git a/examples_async.py b/examples_async.py index dfdb850..abff512 100644 --- a/examples_async.py +++ b/examples_async.py @@ -276,12 +276,16 @@ def on_shutdown(chromed): await tab.wait_loading(5) title = await tab.current_title assert 'GitHub' in title + logger.info('test init tab from chromed OK.') # test on_startup assert chromed.started + logger.info('test on_startup OK.') # ===================== Chrome Test Cases ===================== async with Chrome() as chrome: assert chrome.get_memory() > 0 + logger.info('get_memory OK.') await test_chrome(chrome) + logger.info('test_chrome OK.') # ===================== Tab Test Cases ===================== # Duplicate, use async with chrome.connect_tab(None) instead tab: Tab = await chrome.new_tab() @@ -290,34 +294,46 @@ def on_shutdown(chromed): async with tab(): # test send raw message await test_send_msg(tab) + logger.info('test_send_msg OK.') # test cookies operations await test_tab_cookies(tab) + logger.info('test_tab_cookies OK.') # set url await test_tab_set_url(tab) + logger.info('test_tab_set_url OK.') # test js await test_tab_js(tab) + logger.info('test_tab_js OK.') # test wait_response await test_wait_response(tab) + logger.info('test_wait_response OK.') # test add_js_onload remove_js_onload await test_tab_js_onload(tab) + logger.info('test_tab_js_onload OK.') # test set ua and set headers await test_tab_set_ua_headers(tab) + logger.info('test_tab_set_ua_headers OK.') # load url for other tests await tab.set_url('http://httpbin.org/forms/post') # test current_html await test_tab_current_html(tab) + logger.info('test_tab_current_html OK.') # test screenshot await test_tab_screenshot(tab) + logger.info('test_tab_screenshot OK.') # test double click some positions. test keyboard_send input await test_tab_keyboard_mouse(tab) + logger.info('test_tab_keyboard_mouse OK.') # clear cache assert await tab.clear_browser_cache() + logger.info('clear_browser_cache OK.') # close tab await tab.close() # test chrome.connect_tab async with chrome.connect_tab(chrome.server + '/json', True) as tab: await tab.wait_loading(2) assert 'webSocketDebuggerUrl' in (await tab.current_html) + logger.info('test connect_tab OK.') # close_browser gracefully, I have no more need of chrome instance await chrome.close_browser() # await chrome.kill() @@ -373,7 +389,7 @@ async def tab_callback2(self, tab, url, timeout): results = [await task for task in tasks] assert 1000 < len(results[0]['tags'][0]) < len(results[1]['html']) - logger.critical('test_chrome_engine ok') + logger.critical('test_chrome_engine OK') # asyncio.run will raise aiohttp issue: https://github.com/aio-libs/aiohttp/issues/4324 asyncio.get_event_loop().run_until_complete(_test_chrome_engine()) diff --git a/ichrome/pool.py b/ichrome/pool.py index dd08a27..162353b 100644 --- a/ichrome/pool.py +++ b/ichrome/pool.py @@ -392,6 +392,18 @@ async def preview(self, else: return b'' + async def js(self, + url: str, + js: str, + value_path='result.result', + wait_tag: str = None, + timeout=None) -> bytes: + data = dict(url=url, js=js, value_path=value_path, wait_tag=wait_tag) + return await self.do(data=data, + tab_callback=CommonUtils.js, + timeout=timeout, + tab_index=None) + class CommonUtils: """Some frequently-used callback functions.""" @@ -421,3 +433,8 @@ async def download(self, tab: AsyncTab, data, timeout): result['title'] = title result['encoding'] = encoding return result + + async def js(self, tab: AsyncTab, data, timeout): + await tab.set_url(data['url'], timeout=timeout) + return await tab.js(javascript=data['js'], + value_path=data['value_path']) diff --git a/ichrome/routers/fastapi_routes.py b/ichrome/routers/fastapi_routes.py index d49ab6e..7fbd933 100644 --- a/ichrome/routers/fastapi_routes.py +++ b/ichrome/routers/fastapi_routes.py @@ -27,6 +27,7 @@ # view url with your browser # http://127.0.0.1:8000/chrome/screenshot?url=http://bing.com # http://127.0.0.1:8000/chrome/download?url=http://bing.com +# http://127.0.0.1:8000/chrome/js?url=http://bing.com&js=document.title # ================================================================ @@ -90,6 +91,7 @@ def setup_chrome_engine(self, *args, **kwargs): self.get('/preview')(self.preview) self.get('/download')(self.download) self.get('/screenshot')(self.screenshot) + self.get('/js')(self.js) self.post('/do')(self.do) self.add_event_handler('startup', self._chrome_on_startup) self.add_event_handler('shutdown', self._chrome_on_shutdown) @@ -151,3 +153,17 @@ async def do(self, tab_operation: TabOperation): result = result or {} status_code = 200 if result else 400 return JSONResponse(content=result, status_code=status_code) + + async def js(self, + url: str, + js: str = None, + value_path='result.result', + wait_tag: str = None, + timeout: typing.Union[float, int] = None): + result = await self.chrome_engine.js(url, + js=js, + value_path=value_path, + wait_tag=wait_tag, + timeout=timeout) + status_code = 200 if result else 400 + return JSONResponse(result or {}, status_code)