mirror of
https://github.com/nlohmann/json.git
synced 2026-07-11 13:05:11 +00:00
Fix container input_adapter SFINAE for lvalue-only ADL begin/end (#111)
The container overload of json::parse(c) / accept(c) / sax_parse(c, ...) silently dropped from overload resolution for user types whose ADL begin(T&) / end(T&) accepted only non-const lvalue references (a legitimate pattern matching std::begin semantics). This was because the detection code used std::declval<ContainerType>() which synthesized an rvalue, and the rvalue failed to bind to lvalue-only ADL functions. Fix by making both the outer input_adapter(ContainerType&&) and the factory's create(ContainerType&&) forwarding references, preserving the caller's value category and constness via reference collapsing. This ensures detection (std::declval) and actual use (std::forward) always match without needing decay/remove_reference. - Rewrite input_adapters.hpp container overload with forwarding refs - Add regression tests for lvalue-only non-const ADL begin/end - Add regression test for rvalue containers (no breakage) - Update API docs (parse, accept, sax_parse, from_*) to clarify that begin/end must match std::begin/std::end semantics - Add version history notes for 3.13.0 - Regenerate amalgamation Second-order effect: binary_reader.hpp's internal call to input_adapter(number_vector) now deduces iterator vs const_iterator based on the lvalue; functionally harmless (iterator_input_adapter is iterator-type-agnostic), verified via unit-ubjson/unit-bjdata tests. Closes remaining limitation from #4354 / PR #5218 (todo 106). Signed-off-by: Niels Lohmann <mail@nlohmann.me>
This commit is contained in:
@@ -34,7 +34,8 @@ static basic_json parse(IteratorType first, IteratorType last,
|
||||
- a C-style array of characters
|
||||
- a pointer to a null-terminated string of single byte characters (throws if null)
|
||||
- a `std::string`
|
||||
- an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators.
|
||||
- a container `obj` for which `begin(obj)` and `end(obj)` produce a valid pair of iterators
|
||||
(as found via ADL or member functions, with semantics compatible to `std::begin` and `std::end`)
|
||||
|
||||
`IteratorType`
|
||||
: a compatible iterator type, for instance.
|
||||
@@ -236,6 +237,7 @@ Invalid Unicode escapes and unpaired surrogates in the input are reported as
|
||||
- Ignoring comments via `ignore_comments` added in version 3.9.0.
|
||||
- Changed [runtime assertion](../../features/assertions.md) in case of `FILE*` null pointers to exception in version 3.12.0.
|
||||
- Added `ignore_trailing_commas` in version 3.13.0.
|
||||
- Extended container support (1) to include types with lvalue-only ADL `begin`/`end` (matching `std::begin`/`std::end` semantics) in version 3.13.0.
|
||||
|
||||
!!! warning "Deprecation"
|
||||
|
||||
|
||||
Reference in New Issue
Block a user