Version
6.2.0-SNAPSHOT
What happened?
Description
The spliterators in org.apache.jena.mem.spliterator —
ArraySpliterator, ArraySubSpliterator, SparseArraySpliterator,
and SparseArraySubSpliterator — report Spliterator.IMMUTABLE from
their characteristics() method. This is inconsistent with their
actual behavior: each one snapshots set.size() at construction time
and throws ConcurrentModificationException from tryAdvance /
forEachRemaining when the underlying collection is structurally
modified during traversal.
The Javadoc for Spliterator.IMMUTABLE states that an immutable
spliterator's element source "cannot be structurally modified".
Reporting IMMUTABLE while detecting and reporting structural
modification is a contract violation and can mislead stream pipelines
or downstream callers that inspect characteristics.
Related issue: NONNULL not enforced
The same spliterators also report NONNULL, but the backing map and
set implementations (FastHashMap, FastHashSet, HashCommonMap,
HashCommonSet) accept null keys and values without complaint.
While none of the current internal callers pass null, the interface
contract was not documented and not enforced, so the NONNULL
characteristic was technically also unsubstantiated.
Proposed fix
- Drop
IMMUTABLE from characteristics() in the four spliterators.
- Document on
JenaMap, JenaMapIndexed, JenaSet,
JenaSetHashOptimized, and JenaSetIndexed that null keys/values
are not permitted.
- Add
assert checks on the write paths of the map/set
implementations to catch violations in tests.
Scope
Internal to jena-core memory collections. No public API change; the
affected interfaces are package-internal helpers used by the in-memory
graph stores.
Relevant output and stacktrace
Are you interested in making a pull request?
None
Version
6.2.0-SNAPSHOT
What happened?
Description
The spliterators in
org.apache.jena.mem.spliterator—ArraySpliterator,ArraySubSpliterator,SparseArraySpliterator,and
SparseArraySubSpliterator— reportSpliterator.IMMUTABLEfromtheir
characteristics()method. This is inconsistent with theiractual behavior: each one snapshots
set.size()at construction timeand throws
ConcurrentModificationExceptionfromtryAdvance/forEachRemainingwhen the underlying collection is structurallymodified during traversal.
The Javadoc for
Spliterator.IMMUTABLEstates that an immutablespliterator's element source "cannot be structurally modified".
Reporting
IMMUTABLEwhile detecting and reporting structuralmodification is a contract violation and can mislead stream pipelines
or downstream callers that inspect characteristics.
Related issue: NONNULL not enforced
The same spliterators also report
NONNULL, but the backing map andset implementations (
FastHashMap,FastHashSet,HashCommonMap,HashCommonSet) acceptnullkeys and values without complaint.While none of the current internal callers pass
null, the interfacecontract was not documented and not enforced, so the
NONNULLcharacteristic was technically also unsubstantiated.
Proposed fix
IMMUTABLEfromcharacteristics()in the four spliterators.JenaMap,JenaMapIndexed,JenaSet,JenaSetHashOptimized, andJenaSetIndexedthat null keys/valuesare not permitted.
assertchecks on the write paths of the map/setimplementations to catch violations in tests.
Scope
Internal to
jena-corememory collections. No public API change; theaffected interfaces are package-internal helpers used by the in-memory
graph stores.
Relevant output and stacktrace
Are you interested in making a pull request?
None