NaiboWang/EasySpider · error · RuntimeError
you cannot reuse the ChromeOptions object
Error message
you cannot reuse the ChromeOptions object
What it means
Raised as RuntimeError by undetected_chromedriver's Chrome.__init__ (ExecuteStage/undetected_chromedriver_ES/__init__.py:268) when the SAME ChromeOptions instance is passed to a second Chrome(...) constructor. On first use UC stamps options._session = self; a non-None _session on a later call means the options object is being reused, which would accumulate duplicate --remote-debugging-port / --user-data-dir arguments and conflict at startup.
Source
Thrown at ExecuteStage/undetected_chromedriver_ES/__init__.py:268
self.patcher = Patcher(
executable_path=driver_executable_path,
force=patcher_force_close,
version_main=version_main,
user_multi_procs=user_multi_procs,
)
# self.patcher.auto(user_multiprocess = user_multi_num_procs)
chrome_version = self.patcher.auto()
# self.patcher = patcher
if not options:
options = ChromeOptions()
try:
if hasattr(options, "_session") and options._session is not None:
# prevent reuse of options,
# as it just appends arguments, not replace them
# you'll get conflicts starting chrome
raise RuntimeError("you cannot reuse the ChromeOptions object")
except AttributeError:
pass
options._session = self
if not options.debugger_address:
debug_port = (
port
if port != 0
else selenium.webdriver.common.service.utils.free_port()
)
debug_host = "127.0.0.1"
options.debugger_address = "%s:%d" % (debug_host, debug_port)
else:
debug_host, debug_port = options.debugger_address.split(":")
debug_port = int(debug_port)
if enable_cdp_events:View on GitHub (pinned to 191bd6d754)
Solutions
- Construct a brand-new ChromeOptions() for every uc.Chrome() call (move the options build inside the loop/factory).
- If you need identical settings, wrap the options-building in a helper function and call it each time.
- Do NOT reset opts._session = None to bypass the guard - the accumulated arguments will still conflict.
- If migrating from vanilla selenium where options reuse was tolerated, audit every call site.
Example fix
# before
opts = uc.ChromeOptions()
opts.add_argument('--disable-gpu')
for _ in range(3):
driver = uc.Chrome(options=opts) # 2nd+ iteration throws
# after
def make_opts():
o = uc.ChromeOptions()
o.add_argument('--disable-gpu')
return o
for _ in range(3):
driver = uc.Chrome(options=make_opts()) # fresh each time Defensive patterns
Strategy: validation
Validate before calling
def options_is_consumed(opts) -> bool:
return getattr(opts, '_session', None) is not None
if options_is_consumed(opts):
opts = uc.ChromeOptions() # rebuild before passing to Chrome() Try / catch
import undetected_chromedriver_ES as uc
try:
driver = uc.Chrome(options=opts)
except RuntimeError as e:
if 'cannot reuse the ChromeOptions' in str(e):
opts = uc.ChromeOptions() # rebuild and retry once
driver = uc.Chrome(options=opts)
else:
raise Prevention
- Never hoist a single ChromeOptions to module scope for reuse across drivers.
- In retry/reconnect paths, rebuild options alongside the driver.
- Add a unit test that asserts two drivers can be created from two sibling options objects.
When it happens
Trigger: Construct uc.Chrome(options=opts); later construct uc.Chrome(options=opts) again with the same opts object. The check `hasattr(options, '_session') and options._session is not None` is true on the second call, so RuntimeError is raised before any chrome process starts.
Common situations: Loop/factory code creates one ChromeOptions outside a loop then builds a driver per iteration; retry/reconnect logic reuses the original options; tests spin up a fresh driver per case but share a module-level options constant.
Related errors
- file does not exist: %s
- function call timed out
- dont parse timezone format
- dont parse timezone format
- Element {value} not found in any frame or iframe
AI-assisted analysis of NaiboWang/EasySpider@191bd6d754 (2026-08-13).
Data as JSON: /api/errors/1921cb7a5dda2d6d.
Report an issue: GitHub.