LinkedCaseInsensitiveMap.keySet().remove returns false after removing a null-valued entry
Maintainer thường phản hồi trong vòng 1 ngày
Chưa có ai nhận issue này.
- #37478 của @zsewasdsdsd — đã đóng, không merge
Đánh giá
- Độ khó
- 2/5
- Thời gian dự kiến
- 1-3 giờ
- Mức phù hợp với người mới
- 78/100
Hướng nghiên cứu
Lỗi nằm ở lớp nội KeySet trong LinkedCaseInsensitiveMap.java của spring-core. Tại đó, remove(o) quyết định kết quả boolean dựa trên việc Map.remove có trả về null hay không, nên một entry có giá trị null sẽ báo false. Hãy chạy đoạn Repro.java trong issue với spring-core để xác nhận dòng đầu và dòng thứ ba đều in ra false. Công việc hoàn thành khi keySet().remove và keySet().removeAll trả về true với một key có mặt và giá trị null, và các test hiện có của LinkedCaseInsensitiveMap vẫn chạy thành công.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Mô tả
Affected versions
Verified with the published spring-core 7.0.9 and 6.2.19 artifacts on JDK 21. The same result was reproduced with the affected classes compiled from main at 85a532dce455655aec8fd5a301b37c6c5ceda5bb, with the remaining dependencies supplied by spring-core 7.0.9. This was a focused reproduction, not a full Gradle build.
Problem
LinkedCaseInsensitiveMap supports null values. When a key is mapped to null, keySet().remove(key) removes the entry but returns false. This contradicts the Set removal contract, and also makes keySet().removeAll(...) report no change when it chooses its remove-based path.
Callers relying on the boolean result to detect a change receive the wrong result even though the map was modified.
Minimal reproduction
Save as Repro.java:
import java.util.Locale;
import java.util.Set;
import org.springframework.util.LinkedCaseInsensitiveMap;
public class Repro {
public static void main(String[] args) {
var map = new LinkedCaseInsensitiveMap<String>(Locale.ROOT);
map.put("key", null);
System.out.println(map.keySet().remove("key"));
System.out.println(map.isEmpty());
map.put("key", null);
map.put("other", "value");
System.out.println(map.keySet().removeAll(Set.of("key")));
System.out.println(map.containsKey("key"));
System.out.println(map.size());
}
}
Run on Java 17 or later:
curl -fLO https://repo.maven.apache.org/maven2/org/springframework/spring-core/7.0.9/spring-core-7.0.9.jar
java -cp spring-core-7.0.9.jar Repro.java
Actual output:
false
true
false
false
1
Expected: the first and third lines should be true, because both operations removed an existing key. The remaining lines are correct.
Cause
LinkedCaseInsensitiveMap.KeySet.remove returns LinkedCaseInsensitiveMap.this.remove(o) != null. A null return from Map.remove cannot distinguish an absent key from a present null-valued mapping.
The Java Set.remove contract requires true when the set contained the element and it was removed.
Related reports checked
#22821 / #23644 addressed stale internal key registrations after collection-view removals. This report concerns the boolean return value after a successful removal; the internal key registration is correctly cleared in this reproduction. #37351 concerns computeIfAbsent registrations and is also a separate case. Searches for LinkedCaseInsensitiveMap keySet and LinkedCaseInsensitiveMap null remove did not reveal a direct duplicate.
- Ngôn ngữ chính
- Java
- Star
- 60.3k
- Fork
- 38.7k
- Merge trung bình
- 1 ngày 1 giờ
- Pull request đã merge (30 ngày)
- 33
Chuẩn bị môi trường
- Không có Dockerfile hay tệp Docker Compose
- Không có mẫu pull request
- Đọc 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.
Issue khác của spring-projects/spring-framework
-
status: waiting-for-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 87/100
spring-projects/spring-framework#37613 ·
Maintainer thường phản hồi trong vòng 1 ngày
-
`YamlProcessor.getFlattenedMap` with `includeEmpty` returns a `null` key for an empty root mappingCó thể làm lại được @erfannvb đã nhận 14 ngày trước và không có pull request nào đang mở. Đang mởstatus: waiting-for-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 78/100
spring-projects/spring-framework#37522 · 1 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
`WebClient` with default codecs drops `ProblemDetail` extension membersCó thể làm lại được Pull request cho issue này đã bị đóng mà không được merge. Đang mởstatus: waiting-for-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 70/100
spring-projects/spring-framework#37503 · 1 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
StandardApiVersionDeprecationHandler generates nonconforming Sunset HTTP datesCó thể làm lại được Pull request cho issue này đã bị đóng mà không được merge. Đang mởstatus: waiting-for-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 68/100
spring-projects/spring-framework#37486 · 4 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
FastByteArrayOutputStream input stream rejects valid skip(long) argumentsCó thể làm lại được @hickey-ai đã nhận 17 ngày trước và không có pull request nào đang mở. Đang mởstatus: waiting-for-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 82/100
spring-projects/spring-framework#37471 · 6 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
Tất cả issue của spring-projects/spring-framework
Issue tương tự
-
5.0.x backport enhancement
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 63/100
spring-cloud/spring-cloud-function#1507 ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 65/100
open-learning-exchange/myplanet#18484 ·
Maintainer thường phản hồi trong vòng 1 ngày
-
ai-driven-fuzzing bug claude Minor
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 66/100
linagora/twake-calendar-side-service#1417 · 2 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 74/100
line/armeria#7109 · 3 reaction ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 72/100
open-feature/java-sdk-contrib#1966 ·
Maintainer thường phản hồi trong vòng 1 ngày