diff --git a/hermes_state_readpool.py b/hermes_state_readpool.py index 6eefb841c6..01e63fcac8 100644 --- a/hermes_state_readpool.py +++ b/hermes_state_readpool.py @@ -167,7 +167,11 @@ class _PathReadBudget: warn = (handles > _HANDLES_PER_PATH_WARN and not self._duplicate_handles_warned) if warn: self._duplicate_handles_warned = True - creation_sites = ", ".join(sorted(member._creation_site for member in self._members)) + # Same population as `handles`: the read-only attaches the count skips + # must not reappear in the list, or the list no longer explains the number. + creation_sites = ", ".join(sorted( + member._creation_site for member in self._members if not member.read_only + )) if warn: # Writer connections cannot be capped; the only bound is not opening # redundant handles, so make the duplicate visible before it's an incident. diff --git a/tests/hermes_state/test_session_db_read_conn_pool.py b/tests/hermes_state/test_session_db_read_conn_pool.py index ab2ef47063..662f77b33c 100644 --- a/tests/hermes_state/test_session_db_read_conn_pool.py +++ b/tests/hermes_state/test_session_db_read_conn_pool.py @@ -651,9 +651,14 @@ def test_duplicate_handles_on_one_path_are_reported(db, caplog): def open_extra_handle(): return SessionDB(db_path=db.db_path) + def open_read_only_attach(): + return SessionDB(db_path=db.db_path, read_only=True) + extra = [] try: with caplog.at_level(logging.WARNING, logger="hermes_state"): + # A read-only attach is outside the count (#110934); it must be outside the list too. + extra.append(open_read_only_attach()) for _ in range(_HANDLES_PER_PATH_WARN + 1): extra.append(open_extra_handle()) warnings = [ @@ -668,6 +673,7 @@ def test_duplicate_handles_on_one_path_are_reported(db, caplog): # site must still be available when another caller triggers the warning. assert re.search(rf"{re.escape(__name__)}\.db:\d+", warning) assert len(re.findall(rf"{re.escape(__name__)}\.open_extra_handle:\d+", warning)) == _HANDLES_PER_PATH_WARN + assert "open_read_only_attach" not in warning, "listed a holder the count excludes" finally: for d in extra: d.close()