{"id":953,"hash":"0bf9a3eb9843c54c2ac384fcb2f13bff0cb956235227ec48b79abffbfb904f75","pattern":"&quot;asyncio.run() cannot be called from a running event loop&quot; when using Jupyter Notebook","full_message":"I would like to use asyncio to get webpage html.\n\nI run the following code in jupyter notebook:\n\nimport aiofiles\nimport aiohttp\nfrom aiohttp import ClientSession\n\nasync def get_info(url, session):\n    resp = await session.request(method=\"GET\", url=url)\n    resp.raise_for_status()\n    html = await resp.text(encoding='GB18030')\n    with open('test_asyncio.html', 'w', encoding='utf-8-sig') as f:\n        f.write(html)\n    return html\n    \nasync def main(urls):\n    async with ClientSession() as session:\n        tasks = [get_info(url, session) for url in urls]\n        return await asyncio.gather(*tasks)\n\nif __name__ == \"__main__\":\n    url = ['http://huanyuntianxiazh.fang.com/house/1010123799/housedetail.htm', 'http://zhaoshangyonghefu010.fang.com/house/1010126863/housedetail.htm']\n    result = asyncio.run(main(url))\n\nHowever, it returns RuntimeError: asyncio.run() cannot be called from a running event loop\n\nWhat is the problem?\n\nHow to solve it?","ecosystem":"pypi","package_name":"python-3.x","package_version":null,"solution":"The asyncio.run() documentation says:\n\nThis function cannot be called when another asyncio event loop is running in the same thread.\n\nIn your case, jupyter (IPython ≥ 7.0) is already running an event loop:\n\nYou can now use async/await at the top level in the IPython terminal and in the notebook, it should — in most of the cases — “just work”. Update IPython to version 7+, IPykernel to version 5+, and you’re off to the races.\n\nTherefore you don't need to start the event loop yourself and can instead call await main(url) directly, even if your code lies outside any asynchronous function.\n\nModern Jupyter lab/notebook\nUse the following for newer versions of Jupyter (IPython ≥ 7.0):\n\nasync def main():\n    print(1)\n    \nawait main()\n\nPython or older IPython\nIf you are using Python ≥ 3.7 or IPython < 7.0, use the following:\n\nimport asyncio\n\nasync def main():\n    print(1)\n    \nasyncio.run(main())\n\nThat's also that form you should use if you are running this in a python REPL or in an independent script (a bot, a web scrapper, etc.).\n\nIf you are using an older version of python (< 3.7), the API to run asynchronous code was a bit less elegant:\n\nimport asyncio\n\nasync def main():\n    print(1)\n    \nloop = asyncio.get_event_loop()\nloop.run_until_complete(hello_world())\n\nUsing await in your code\nIn your case, you can call await main(url) as follows:\n\nurl = ['url1', 'url2']\nresult = await main(url)\n\nfor text in result:\n    pass # text contains your html (text) response\n\nThis change to recent versions of IPython makes notebook code simpler and more intuitive for beginers.\n\nFurther notices\nFew remarks that might help you in different use cases.\n\nJupyter vs. IPython caution\nThere is a slight difference on how Jupyter uses the loop compared to IPython.\n\n[...] IPykernel having a persistent asyncio loop running, while Terminal IPython starts and stops a loop for each code block.\n\nThis can lead to unexpected issues.\n\nGoogle Colab\nIn the past, Google colab required you to do more complex loop manipulations like presented in some other answers here. Now plain await main() should just work like in IPython ≥ 7.0 (tested on Colab version 2023/08/18).\n\nPython REPL\nYou can also run the python REPL using the asyncio concurrent context. As explained in asyncio's documentation:\n\n$ python -m asyncio\nasyncio REPL ...\nUse \"await\" directly instead of \"asyncio.run()\".\n>>> import asyncio\n>>> await asyncio.sleep(10, result='hello')\n'hello'\n\nThe asyncio REPL should be available for python ≥ 3.8.1.\n\nWhen does asyncio.run matters and why?\nOlder versions of IPython were running in a synchronous context, which is why calling asyncio.run was mandatory.\n\nThe asyncio.run function allows to run asynchronous code from a synchronous context by doing the following:\n\nstarts an event loop,\nruns the async function passed as argument in this (new) event loop,\nstops the event loop once the function returned\n\nIn more technical terms (notice how the argument function is called a coroutine):\n\nThis function runs the passed coroutine, taking care of managing the asyncio event loop, finalizing asynchronous generators, and closing the threadpool.\n\nWhat happen when using await in synchronous context?\nIf you happen to use await in a synchronous context you would get the one of the following errors:\n\nSyntaxError: 'await' outside function\nSyntaxError: 'await' outside async function\n\nIn that case that means you need to use asyncio.run(main()) instead of await main().","confidence":0.95,"source":"stackoverflow","source_url":"https://stackoverflow.com/questions/55409641/asyncio-run-cannot-be-called-from-a-running-event-loop-when-using-jupyter-no","votes":219,"created_at":"2026-04-19T04:52:05.805799+00:00","updated_at":"2026-04-19T04:52:05.805799+00:00"}