configparser: whitespace-ending delimiter with an empty value cannot be parsed (write() output is unreadable)
Chưa có ai nhận issue này.
- Ngôn ngữ chính
- Python
- Star
- 77.2k
- Fork
- 35.9k
- Chỉ số merge pull request
- Chỉ số pull request đang chờ
Mô tả
Bug report
The whitespace-in-delimiters feature added in gh-156353 (3.16) cannot parse an option that has an empty value when the delimiter ends in whitespace — including its own write() output.
_read matches option lines against line.clean, which is val.strip() (both sides) with comments removed. For a whitespace delimiter, the delimiter is the trailing whitespace, so strip() erases it and OPTCRE no longer matches.
Reproduction (on main, 3.16.0a0)
import configparser, io
# (1) plain read — rejected, though the option regex itself matches "key ":
cp = configparser.ConfigParser(delimiters=(' ',))
cp.read_string("[s]\nkey \n") # -> ParsingError (expected: {'key': ''})
# (2) round-trip — write() emits a line read_string() then refuses to parse:
w = configparser.ConfigParser(delimiters=(' ',)); w['s'] = {'key': ''}
buf = io.StringIO(); w.write(buf)
print(repr(buf.getvalue())) # '[s]\nkey \n\n'
configparser.ConfigParser(delimiters=(' ',)).read_string(buf.getvalue()) # ParsingError
A serializer that cannot read its own output is a clear self-inconsistency. Empty values are a supported, first-class feature for every other delimiter (key=, key:, key->, key|| all read back as {'key': ''}), so whitespace delimiters should behave the same.
Bug class
Any delimiter whose string ends in whitespace combined with an empty (or all-whitespace) value: ' ', '\t', ' ', 'x ', '= ' all raise; delimiters without trailing whitespace ('->', ' x') work.
Why it's not caught
The gh-156353 tests (test_space_delimiter, test_any_delimiter) only use non-empty values, so this edge is unpinned.
Fix
Match the option regex against a form that preserves trailing whitespace (the delimiter). optval is already stripped after the match, so ordinary values keep no trailing whitespace and the other uses of line.clean are unaffected. I have a small patch + tests and will open a PR referencing this issue.
Found with AI assistance; I've reproduced and verified the behaviour and fix on a locally built interpreter and understand them.
Linked PRs
- gh-157457
Hướng dẫn đóng góp
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Hướng nghiên cứu
Bắt đầu với ConfigParser._read và phạm vi kiểm thử hiện có của test_space_delimiter và test_any_delimiter được mô tả trong issue. Tái hiện các trường hợp giá trị rỗng bằng read_string() và write(), sau đó mở rộng các bài kiểm thử để các dấu phân cách kết thúc bằng khoảng trắng và các giá trị rỗng được phân tích nhất quán, đồng thời round trip thành công.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Đánh giá
- Công nghệ
- python
- Lĩnh vực
- tooling
- Loại issue
- Lỗi
- Độ khó
- 3/5
- Thời gian dự kiến
- 1-2 ngày
- Mức độ hoạt động
- Đình trệ
- Độ rõ ràng
- Đặc tả rõ ràng
- Mức phù hợp với người mới
- 25/100