Skip to content

Bookmark file-input restore leaks a TemporaryDirectory when a session never ends #2482

Description

@schloerke

Summary

A tempfile.TemporaryDirectory created while restoring a bookmarked file input is cleaned up only via session.on_ended(). If the session never ends, the directory survives until the object is garbage collected, at which point tempfile emits a ResourceWarning: Implicitly cleaning up <TemporaryDirectory ...>.

https://github.com/posit-dev/py-shiny/blob/main/shiny/input_handler.py#L252-L254

if len(value_list) > 0:
    tempdir_root = tempfile.TemporaryDirectory()
    session.on_ended(lambda: tempdir_root.cleanup())

Impact

Low. In a running app the session ends and the callback fires, so this is mostly a test-environment artifact — a unit test that builds a session and never closes it leaves the directory to the collector.

It became visible when the unit suite adopted filterwarnings = error in #2480: the ResourceWarning is raised inside a finalizer, becomes an unraisable exception, and pytest reports it as a PytestUnraisableExceptionWarning against whichever test happened to be running when the collector fired (test_theme_css_compiles_and_is_cached on the oldest-deps job). Because the attribution is random, ResourceWarning is now ignored in pytest.ini; that ignore hides this leak rather than fixing it.

Note that shiny/ui/_theme.py deliberately relies on GC-time cleanup for its own temp directories (see theme_temporary_directories), so it is a second, intentional source of the same warning class.

Possible resolutions

  1. Leave as-is and close — the on-ended cleanup is correct for real sessions, and the warning only appears in tests.
  2. Make the test harness close its sessions, so the callback runs and the ignore in pytest.ini can be narrowed or dropped.
  3. Suppress the warning at the source by cleaning up deterministically where the lifetime is known.

Filing this so the decision is recorded rather than lost behind the pytest.ini ignore.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Priority: LowLow-impact bug, docs polish, papercut, or unclear low-severity request.ai-triage:doneMarks an issue whose AI triage workflow is complete.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions