Skip to content
Closed

AI junk #3784

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@ Unreleased
prompt when the output stream does not support them, matching `echo()`.
This stripping was lost in `8.4.0` when {pr}`2969` began writing the
prompt with `input()` directly. {issue}`3572` {pr}`3653`
- Lazy read-mode {class}`File` parameters no longer eagerly open FIFO paths,
which could consume a writer's data before the command accesses the file.
{issue}`2645`
- Fix test failures when using pytest >= 9.1. {pr}`3656`
- {class}`Path` with `allow_dash=True` no longer triggers a `BytesWarning`,
an error under `python -bb`, when checking a value against the `-`
Expand Down
13 changes: 12 additions & 1 deletion src/click/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import collections.abc as cabc
import os
import re
import stat
import sys
import typing as t
from functools import update_wrapper
Expand Down Expand Up @@ -146,10 +147,20 @@ def __init__(
if self.name == "-":
self._f, self.should_close = open_stream(filename, mode, encoding, errors)
else:
is_fifo = False

if "r" in mode:
try:
is_fifo = stat.S_ISFIFO(os.stat(filename).st_mode)
except OSError:
pass

if "r" in mode and not is_fifo:
# Open and close the file in case we're opening it for
# reading so that we can catch at least some errors in
# some cases early.
# some cases early. Do not do this for FIFOs because an
# eager read can consume the writer's data before the lazy
# file is accessed.
open(filename, mode).close()
self._f = None
self.should_close = True
Expand Down
20 changes: 20 additions & 0 deletions tests/test_utils/test_LazyFile.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
import builtins
import os

import pytest

import click


Expand All @@ -9,3 +14,18 @@ def test_iter_lazyfile(tmpdir):
with click.utils._LazyFile(f.name) as lf:
for e_line, a_line in zip(expected, lf, strict=False):
assert e_line == a_line.strip()


@pytest.mark.skipif(not hasattr(os, "mkfifo"), reason="FIFOs are not supported.")
def test_lazyfile_does_not_eagerly_open_fifo(tmp_path, monkeypatch):
"""Issue #2645: lazy read-mode files must not consume FIFO input early."""
path = tmp_path / "input"
os.mkfifo(path)

def unexpected_open(*args, **kwargs):
raise AssertionError("lazy FIFO setup should not open the file")

monkeypatch.setattr(builtins, "open", unexpected_open)
lazy_file = click.utils._LazyFile(path, "rb")

assert lazy_file._f is None