Commit Graph
5025 Commits
Author SHA1 Message Date
Niels LohmannandGitHub c2e1cc50e0 docs: document the complexity of ordered_map operations (#5353)
* docs: document the complexity of ordered_map operations

ordered_map stores its elements in a std::vector in insertion order and
has no lookup index, so emplace, operator[], at, find, count, erase, and
insert are all linear scans. The documentation stated no complexity for
any operation, neither in ordered_map.md nor in ordered_json.md.

Add a per-operation complexity table and note the consequence: building
or parsing an ordered_json object of n keys is O(n^2). Measured with
-O2 -DNDEBUG for parsing a flat object of n keys, ordered_json is 5x
slower than json at n=2000 and 54x slower at n=16000, with the timings
quadrupling per doubling of n. Cross-reference the table from
ordered_json.md and from the object order page, which recommends
ordered_json without mentioning the cost.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* docs: move the Complexity section after Member functions

scripts/check_structure.py enforces a fixed section order for pages under
docs/mkdocs/docs/api, in which Complexity comes after Member functions.
The section had been placed right after Iterator invalidation, which made
ci_test_build_documentation fail with structure/section_order.

No content change beyond the move; the table columns are realigned to the
narrower content.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-08-04 08:45:35 +02:00
Niels LohmannandGitHub 173f2a7407 Documentation review: exceptions from binary-format hardening, and tuple reference types (#5359)
* 📝 Document exceptions newly thrown by the binary-format hardening

A round of binary-format input validation (#5274, #5284, #5287, #5332)
added new failure modes without updating exceptions.md, and left two
descriptions factually narrower than the code:

- parse_error.110 said "CBOR or MessagePack"; BSON and UBJSON also
  throw it. Generalized, and added the BSON EOF example (#5332).
- parse_error.112: added the BSON document-size mismatch example
  (#5287).
- parse_error.113 said "while parsing a map key", but its own existing
  UBJSON char example already contradicted that. Broadened to cover
  invalid length specifications, and added the negative-string-length
  example (#5284).
- out_of_range.408 said "of an UBJSON array or object"; CBOR now throws
  it too (#5274). Generalized and added both CBOR examples.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* 📝 Correct which types may be referenced in a tuple extraction

The note added in #5271 said a referenced type must be one the library
stores "or an arithmetic type it can convert to/from". The parenthetical
is wrong: is_compatible_reference_type requires an exact match against
the stored types, so std::tuple<int&> is rejected by static_assert even
though int converts fine as a value. Only the value case is permissive.

Spell out the eight admissible types, give the int& counter-example, and
separate the reference restriction from by-value conversion.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-08-04 08:45:18 +02:00
Niels LohmannandGitHub 1c63a120b6 docs: document how discarded values are removed by the parser callback (#5354)
Follow-up to #5342, which fixed the parser callback leaving a discarded
member behind when an array or a value under an object key was rejected.
The documentation of parser_callback_t only stated that discarded values
in structured types are skipped, without saying that this covers object
parents and that the key is removed along with the value, so there was no
way to tell the fixed behavior from the buggy one.

Spell out the discarding rules, add an example that exercises the cases
the fix repaired, and correct the return value description: a discarded
top-level value is replaced by null, not by "an empty discarded object".

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-08-04 08:45:02 +02:00
Niels LohmannandGitHub 85889e8843 docs: use HTTPS for the astyle and cppcheck links in README (#5351)
* docs: use HTTPS for the astyle and cppcheck links in README

Both links were still `http://`. `astyle.sourceforge.net` serves HTTPS
directly; `cppcheck.sourceforge.net` redirects to
`https://cppcheck.sourceforge.io`, which is also the URL already used in
`docs/mkdocs/docs/community/quality_assurance.md`, so the redirect is
skipped here.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* CI: suppress -Wc2y-extensions for Clang

Clang 22.1 (now shipped by silkeh/clang:latest) diagnoses __COUNTER__ as a
C2y extension, and does so in C++ mode as well. Under -Weverything -Werror
this breaks every ci_test_clang_cxx* / ci_test_clang_libcxx_cxx* target,
independently of the code under test.

The library itself does not use __COUNTER__; all diagnostics originate in
vendored Doctest (DOCTEST_ANONYMOUS, used by TEST_CASE and SECTION).

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-08-04 08:43:59 +02:00
dependabot[bot]GitHubdependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
3c0a9a99fd ⬆️ Bump actions/stale from 10.4.0 to 11.0.0 (#5350)
Bumps [actions/stale](https://github.com/actions/stale) from 10.4.0 to 11.0.0.
- [Release notes](https://github.com/actions/stale/releases)
- [Changelog](https://github.com/actions/stale/blob/main/CHANGELOG.md)
- [Commits](https://github.com/actions/stale/compare/1e223db275d687790206a7acac4d1a11bd6fe629...4391f3da665fdf50b6810c1a66712fb9ba21aa93)

---
updated-dependencies:
- dependency-name: actions/stale
  dependency-version: 11.0.0
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-08-03 20:50:15 +02:00
dependabot[bot]GitHubdependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
e82724d87f ⬆️ Bump coverallsapp/github-action from 2.3.7 to 2.3.8 (#5349)
Bumps [coverallsapp/github-action](https://github.com/coverallsapp/github-action) from 2.3.7 to 2.3.8.
- [Release notes](https://github.com/coverallsapp/github-action/releases)
- [Commits](https://github.com/coverallsapp/github-action/compare/5cbfd81b66ca5d10c19b062c04de0199c215fb6e...8d6379e14d29928660c4ba802d8e85393440b329)

---
updated-dependencies:
- dependency-name: coverallsapp/github-action
  dependency-version: 2.3.8
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-08-03 20:50:05 +02:00
78821cd9c2 docs: document standards compliance and parse() vs operator>> strictness (#5326)
* docs: document RFC 8259 / JSONTestSuite compliance and parse() vs operator>> strictness

The compliance story lived only in tests/src/unit-testsuites.cpp, so
drive-by comparisons kept claiming the library "does not fully pass
JSONTestSuite". Make it discoverable:

- README: add a "Standards compliance" note stating that both nst
  JSONTestSuite revisions run in CI, that all mandatory y_/n_ cases pass
  through the strict parse() entry point, and listing the deliberate
  implementation-defined i_ choices (unbounded nesting, silent BOM
  stripping, noncharacters forwarded, strict rejection of invalid UTF-8
  and lone surrogates, out_of_range.406 on numeric overflow).
- features/parsing: add a "Strictness and trailing data" section
  documenting that parse() is strict and rejects trailing data while
  operator>> follows relaxed iostream semantics (parses one value and
  leaves the stream positioned after it) -- the single place a naive
  test yields a "non-compliant" result.

Documentation only; no parser behavior change. Closes #5290.

Signed-off-by: manon <youdie006@users.noreply.github.com>

* docs: correct test-data vendoring and parse()/operator>> claims per review

- README: the JSONTestSuite data is downloaded from nlohmann/json_test_data at
  configure time, not vendored/committed; say so.
- README: only the updated suite runs y_ and n_ cases through strict parse();
  the original suite's y_ cases go through operator>>. Narrow the claim.
- parsing/index.md and operator_gtgt.md: note that operator>> consumes a number's
  terminating byte, so concatenated numbers must be whitespace-separated (1 2
  works, 1true does not); structural and literal values are unaffected.

Signed-off-by: manon <youdie006@users.noreply.github.com>

---------

Signed-off-by: manon <youdie006@users.noreply.github.com>
Co-authored-by: manon <youdie006@users.noreply.github.com>
2026-08-03 19:15:53 +02:00
Angadi56andGitHub 68f0722a19 remove discarded array from parent object in end_array (#5342)
* remove discarded array from parent object in end_array

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

* remove discarded scalar value from parent object in handle_value

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

---------

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>
2026-08-03 19:13:31 +02:00
Angadi56andGitHub 5f121d8c50 avoid sign extension in char_traits<signed char>::to_int_type (#5336)
* avoid sign extension in char_traits<signed char>::to_int_type

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

* spell out-of-range signed char constants as negative values (MSVC C4309)

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

---------

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>
2026-08-03 08:35:53 +02:00
Niels LohmannandGitHub 585929bff9 Fix Clang deprecation warning for json_pointer operator== with ordered_json (#5289)
is_comparable used a flat && chain to both exclude json_pointer/string
comparisons (added for #4621) and check whether Compare(A, B) is well-formed.
Naming std::is_constructible<decltype(...)> as a later operand of that chain
still causes the decltype to be substituted regardless of the first
operand's value, since the operands aren't lazily deferred like
std::conjunction would defer them. That instantiates the transparent
std::equal_to<>::operator() used by ordered_json, whose noexcept-specifier
evaluates the deprecated json_pointer/string operator==, which Clang (unlike
GCC in this case) warns about even though the result is discarded.

Split is_comparable so the Compare(A, B) checks live in a separate helper
that is only referenced from the specialization selected when
is_json_pointer_of is false, so the decltype is never written when A/B are
a json_pointer/string pair, regardless of compiler.

Signed-off-by: Niels Lohmann <niels.lohmann@gmail.com>
2026-08-03 08:20:41 +02:00
Niels LohmannandGitHub 31ba5208c8 docs: qualify the operator>> stream positioning guarantee (#5343)
operator>>'s notes state that it leaves the stream positioned right
after the parsed value, so that concatenated JSON values can be read
back to back. That does not hold when the value is a number: a number
is only terminated by the character that follows it, and the lexer's
unget() is simulated (it rewinds only the lexer's own bookkeeping),
so that character stays consumed from the stream.

Document the actual behaviour: the guarantee holds for all value types
except numbers, which must be followed by whitespace. Also qualify the
cross-reference on the JSON Lines page, which repeated the unqualified
claim.

Documentation only; the behaviour itself is tracked in #5340.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-08-03 08:18:03 +02:00
tomatotomataandGitHub 2222d386c9 fix: check CBOR tagged subtype reads (#5339) 2026-07-31 22:06:55 +02:00
dependabot[bot]GitHubdependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
eaedec859a ⬆️ Bump the codeql-action group with 4 updates (#5341)
Bumps the codeql-action group with 4 updates: [github/codeql-action/init](https://github.com/github/codeql-action), [github/codeql-action/autobuild](https://github.com/github/codeql-action), [github/codeql-action/analyze](https://github.com/github/codeql-action) and [github/codeql-action/upload-sarif](https://github.com/github/codeql-action).


Updates `github/codeql-action/init` from 4.37.2 to 4.37.3
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/e0647621c2984b5ed2f768cb892365bf2a616ad1...e4fba868fa4b1b91e1fdab776edc8cfbe6e9fb81)

Updates `github/codeql-action/autobuild` from 4.37.2 to 4.37.3
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/e0647621c2984b5ed2f768cb892365bf2a616ad1...e4fba868fa4b1b91e1fdab776edc8cfbe6e9fb81)

Updates `github/codeql-action/analyze` from 4.37.2 to 4.37.3
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/e0647621c2984b5ed2f768cb892365bf2a616ad1...e4fba868fa4b1b91e1fdab776edc8cfbe6e9fb81)

Updates `github/codeql-action/upload-sarif` from 4.37.2 to 4.37.3
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/e0647621c2984b5ed2f768cb892365bf2a616ad1...e4fba868fa4b1b91e1fdab776edc8cfbe6e9fb81)

---
updated-dependencies:
- dependency-name: github/codeql-action/init
  dependency-version: 4.37.3
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/autobuild
  dependency-version: 4.37.3
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/analyze
  dependency-version: 4.37.3
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/upload-sarif
  dependency-version: 4.37.3
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-07-31 20:45:32 +02:00
Angadi56andGitHub d94cbd99dc reject CBOR array/map length equal to the indefinite-length marker (#5274)
* reject CBOR array/map length equal to the indefinite-length marker

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

* reject CBOR lengths that do not fit in std::size_t via value_in_range_of

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

---------

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>
2026-07-31 18:04:30 +02:00
bc48951128 Fix UBJSON high-precision floating-point overflow handling (#5323)
This adds a std::isfinite check to the UBJSON floating-point parsing path, throwing out_of_range.406 on overflow. This makes the UBJSON parser's behavior consistent with the normal JSON parser. Fixes #5322.

Signed-off-by: AJ369ninja <abhishek.j@iitg.ac.in>
Co-authored-by: AJ369ninja <abhishek.j@iitg.ac.in>
2026-07-31 18:04:13 +02:00
Angadi56andGitHub fd72ecfc8c validate ndarray element types in write_bjdata_ndarray (#5301)
* validate ndarray element types in write_bjdata_ndarray

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

* read ndarray elements through get<> instead of a fixed union member

_ArrayType_ names the wire type, not how the value is stored: parsing
keeps a non-negative integer as number_unsigned while the C++ API keeps
an int literal as number_integer. Selecting the union member from the
type marker therefore reads the inactive alternative for one of the two,
so read through get<> instead, which dispatches on the active member.

Also reject a negative _ArraySize_ entry, which is not a usable
dimension, and cover the parse-built path in the tests.

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>

---------

Signed-off-by: Angadi Yashaswini <angadi@digiscrypt.com>
2026-07-31 08:52:27 +02:00
YingqiDuanandGitHub de8a099ba5 Document BSON interoperability and subtype-less binary round trips (#5330)
- warn about BSON marker 0x11 interoperability in both directions
- explain subtype-less binary normalization to subtype 0x00
- add a round-trip test for binary values without a subtype

Signed-off-by: YingqiDuan <141370165+YingqiDuan@users.noreply.github.com>
2026-07-31 08:33:07 +02:00
Yash BavadiyaandGitHub dd24e2dffd check all BSON reads and add an EOF check for booleans (#5332)
Signed-off-by: Yash Bavadiya <krbavadiya11@gmail.com>
2026-07-30 23:44:31 +02:00
Patrick10199andGitHub 868506dcc0 Fix CBOR half-float assertion bounds (#5335)
Signed-off-by: Patrick Armstrong <patrick@erpassistant.ai>
2026-07-30 23:38:13 +02:00
dependabot[bot]GitHubdependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
58ce09dcfd ⬆️ Bump the codeql-action group with 4 updates (#5329)
Bumps the codeql-action group with 4 updates: [github/codeql-action/init](https://github.com/github/codeql-action), [github/codeql-action/autobuild](https://github.com/github/codeql-action), [github/codeql-action/analyze](https://github.com/github/codeql-action) and [github/codeql-action/upload-sarif](https://github.com/github/codeql-action).


Updates `github/codeql-action/init` from 4.37.1 to 4.37.2
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/7188fc363630916deb702c7fdcf4e481b751f97a...e0647621c2984b5ed2f768cb892365bf2a616ad1)

Updates `github/codeql-action/autobuild` from 4.37.1 to 4.37.2
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/7188fc363630916deb702c7fdcf4e481b751f97a...e0647621c2984b5ed2f768cb892365bf2a616ad1)

Updates `github/codeql-action/analyze` from 4.37.1 to 4.37.2
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/7188fc363630916deb702c7fdcf4e481b751f97a...e0647621c2984b5ed2f768cb892365bf2a616ad1)

Updates `github/codeql-action/upload-sarif` from 4.37.1 to 4.37.2
- [Release notes](https://github.com/github/codeql-action/releases)
- [Changelog](https://github.com/github/codeql-action/blob/main/CHANGELOG.md)
- [Commits](https://github.com/github/codeql-action/compare/7188fc363630916deb702c7fdcf4e481b751f97a...e0647621c2984b5ed2f768cb892365bf2a616ad1)

---
updated-dependencies:
- dependency-name: github/codeql-action/init
  dependency-version: 4.37.2
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/autobuild
  dependency-version: 4.37.2
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/analyze
  dependency-version: 4.37.2
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
- dependency-name: github/codeql-action/upload-sarif
  dependency-version: 4.37.2
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: codeql-action
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-07-30 22:12:23 +02:00
dependabot[bot]GitHubdependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
8dacb98041 ⬆️ Bump ossf/scorecard-action from 2.4.3 to 2.4.4 (#5337)
Bumps [ossf/scorecard-action](https://github.com/ossf/scorecard-action) from 2.4.3 to 2.4.4.
- [Release notes](https://github.com/ossf/scorecard-action/releases)
- [Changelog](https://github.com/ossf/scorecard-action/blob/main/RELEASE.md)
- [Commits](https://github.com/ossf/scorecard-action/compare/4eaacf0543bb3f2c246792bd56e8cdeffafb205a...2d1146689b8cda280b9bc96326124645441f03bc)

---
updated-dependencies:
- dependency-name: ossf/scorecard-action
  dependency-version: 2.4.4
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2026-07-30 22:11:56 +02:00
Luke BanicevicandGitHub 2e23687092 to_bson() silently emits corrupt documents when a length exceeds INT32_MAX (#5314) 2026-07-28 09:08:57 +00:00
dependabot[bot]andGitHub 227c5cdfb1 ⬆️ Bump mkdocs-material from 9.7.6 to 9.7.7 in /docs/mkdocs (#5324) 2026-07-27 17:36:07 +00:00
dependabot[bot]andGitHub 0832fd1cb4 ⬆️ Bump lukka/get-cmake from 4.3.4 to 4.4.0 (#5303) 2026-07-27 12:40:58 +00:00
Luke BanicevicandGitHub 8ec98e2c9e adding cleanups to bson writer (#5313) 2026-07-27 10:11:10 +00:00
dependabot[bot]andGitHub 88b28ac43c ⬆️ Bump actions/checkout from 7.0.0 to 7.0.1 (#5302) 2026-07-26 23:28:28 +00:00
dependabot[bot]andGitHub e0c3c819e1 ⬆️ Bump the codeql-action group across 1 directory with 4 updates (#5300) 2026-07-26 21:41:52 +00:00
Niels LohmannandGitHub 06ac77f4fd Remove Lion Yang from sponsors list (sponsorship cancelled) (#5306) 2026-07-26 19:42:28 +00:00
Luke BanicevicandGitHub dfa51af692 Enhance documentation on serializing untrusted input in dump() (#5304) 2026-07-26 08:29:31 +00:00
Niels LohmannandGitHub d0d29039da ci: retry ubuntu-toolchain-r PPA add to survive Launchpad flakiness (#5305) 2026-07-25 19:57:26 +00:00
Angadi56andGitHub 9a3ebb9456 validate BSON document size against the bytes read (#5287) 2026-07-23 19:51:40 +00:00
Luke BanicevicandGitHub 3296a3ad8c Docs: clarify there is no official npm package (impersonation/typosquat awareness) (#5299) 2026-07-23 16:02:29 +00:00
Angadi56andGitHub 3565f40229 reject negative UBJSON/BJData string length (#5284) 2026-07-20 20:32:38 +00:00
Angadi56andGitHub 1c5a953de5 reject unpaired UTF-16 surrogates in wide-string input (#5276) 2026-07-19 18:33:42 +02:00
dependabot[bot]andGitHub a03e65420c ⬆️ Bump the codeql-action group with 4 updates (#5275) 2026-07-18 13:59:20 +02:00
dependabot[bot]andGitHub d6ede37088 ⬆️ Bump actions/stale from 10.3.0 to 10.4.0 (#5277) 2026-07-18 13:58:45 +02:00
Niels LohmannandGitHub 722c03495f Extend std::optional null regression coverage (assignment, get_to) (#5269) 2026-07-12 09:16:25 +02:00
Niels LohmannandGitHub c197feff81 Extend memcpy fast path to sized sentinels (e.g. std::counted_iterator) (#5268) 2026-07-12 09:16:06 +02:00
Niels LohmannandGitHub b2b47c69b1 📝 Document std::pair/std::tuple conversion and C++20 range-view construction (#5271)
Both had zero documentation anywhere in docs/mkdocs/. The tuple/pair
gap was first spotted in the very first git-log audit pass but never
turned into an actionable todo, so it persisted uncaught across four
subsequent passes.

- Document basic positional std::pair/std::tuple <-> json array
  conversion, plus #5016's reference-extraction capability
  (get<std::tuple<T&, T&>>() returning references into the stored
  array elements).
- Document #5205's new json-from-C++20-range-view constructor
  (e.g. nums | std::views::filter(...)).

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-11 23:58:49 +02:00
6a406ee141 Document that JSON_Diagnostics CMake option doesn't apply to pre-installed packages (#5270)
Closes #3106. set(JSON_Diagnostics ON) before find_package() has no
effect on a package built and installed elsewhere (Homebrew, vcpkg, a
system package, etc.) -- the compile definition is baked into the
exported nlohmann_jsonTargets.cmake at install time and the generated
config script never re-reads that variable. Verified empirically
against the real Homebrew-installed 3.12.0 package: the exported
target carries a fixed $<$<BOOL:OFF>:JSON_DIAGNOSTICS=1>, and the
suggested set(JSON_Diagnostics ON) snippet produces no change in
exception output.

Documents the actual working fix (overriding the imported target's
INTERFACE_COMPILE_DEFINITIONS property after find_package()) and the
multi-target "JSON_DIAGNOSTICS redefined" pitfall reported earlier in
the issue thread.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
Co-authored-by: Claude Sonnet 5 <noreply@anthropic.com>
2026-07-11 23:58:18 +02:00
Niels LohmannandGitHub ca76c37650 Add iterator+sentinel tests and docs for binary deserializers (#5265)
* Add iterator+sentinel tests and docs for binary deserializers

This commit extends the C++20 ranges support (iterator+sentinel pairs) to the
binary format deserializers from_cbor, from_msgpack, from_ubjson, from_bjdata,
and from_bson, matching what was already done for parse(), accept(), and
sax_parse().

Changes:
- Add istreambuf_sentinel helper to test_utils.hpp for EOF detection in tests
- Add 5 new test cases that read binary files directly via
  std::istreambuf_iterator<char> + sentinel, without pre-buffering
- Update documentation for all 5 from_* functions to document overload (3)
  with SentinelType parameter
- All tests pass; verified against existing test suite data
- Fix potential buffer over-read warning in heterogeneous iterator test

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Merge iterator+sentinel overloads and fix ambiguity/CI issues

Address PR review feedback and CI failures:

- Merge the separate same-type and sentinel-type iterator overloads of
  parse(), accept(), sax_parse(), and the five from_* binary deserializers
  into a single overload with SentinelType defaulted to IteratorType,
  as suggested in review. Applied the same simplification to the
  detail::input_adapter() free functions.
- Fix a latent ambiguity: some compilers (e.g. GCC 4.8) unreliably SFINAE
  the operator!= detection for std::nullptr_t against container/string
  types, making calls like parse(s, nullptr, ...) ambiguous with the
  compatible-input overload. can_compare_ne now explicitly excludes
  std::nullptr_t as a SentinelType.
- Use a named enable_if_t template parameter instead of an unnamed
  function parameter for the SFINAE guard, fixing a clang-tidy
  hicpp-named-parameter/readability-named-parameter failure.
- Update parse.md, accept.md, sax_parse.md, and the five from_*.md pages
  to document the merged overload instead of separate (2)/(3) overloads,
  also fixing an over-160-char line that broke the documentation
  style_check CI job.
- Rework the BSON iterator+sentinel test to parse a BSON file already
  present in the test suite instead of writing/deleting a temp file.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix -Wunneeded-internal-declaration for CustomSentinel in test

CustomSentinel lives in an anonymous namespace (internal linkage), and
the library's parse loop only ever evaluates the iterator-first
direction (it != last), so the reversed-order friend operator!= was
never referenced. Clang's -Weverything flags such unused internal
declarations as an error. Drop the unused overload; the used direction
is enough to satisfy can_compare_ne's either-order detection.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix clang-tidy hicpp-named-parameter and misc-const-correctness

- Drop the unused reversed-order operator!= overload from
  utils::istreambuf_sentinel (only iterator != sentinel is ever
  evaluated) and name the remaining friend's sentinel parameter, fixing
  hicpp-named-parameter/readability-named-parameter.
- Mark the istreambuf_iterator first/last helper variable const in the
  five binary-format sentinel tests, fixing misc-const-correctness.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix clang-tidy misc-const-correctness in heterogeneous sentinel test

json_str is only read via .data()/.size() and never reassigned, so
clang-tidy correctly flags it as const-able. Verified against the exact
CI job (silkeh/clang:dev, ci_clang_tidy target) by running clang-tidy
directly on this file plus the five binary-format sentinel tests
touched by prior commits; all are now clean.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-11 15:09:28 +02:00
Niels LohmannandGitHub fe2bcc080f Custom BinaryType direct assignment (#5266)
* Fix discussion #4209: custom BinaryType direct assignment and extraction

When a custom BinaryType is configured (other than the default std::vector<uint8_t>),
users can now:
1. Assign values of that type directly to create binary values (not arrays)
2. Extract binary values back to that type with get<>()
3. Extract arrays to that type (for backward compatibility)

Implementation:
- Add is_compatible_binary_type trait to centralize SFINAE condition
- Update to_json to accept custom BinaryType values directly
- Update from_json to handle both binary and array inputs for custom BinaryType
- Add #include <vector> with IWYU comment to from_json.hpp
- Add comprehensive tests for assignment and array extraction
- Update binary_t documentation with example

This is purely additive and invisible to the default nlohmann::json alias, which
continues to treat std::vector<uint8_t> as arrays.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix CI: missing include and const-correctness

- Add #include <vector> to type_traits.hpp for the new
  is_compatible_binary_type trait's std::vector<std::uint8_t> reference
  (caught by cpplint's include-what-you-use check)
- Mark test-local json variables const where never reassigned
  (caught by clang-tidy's misc-const-correctness check)

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-11 15:09:05 +02:00
Federico SfrisoandGitHub c60217e801 fix: support constructing json from C++20 range views (#4916) (#5205) 2026-07-11 09:13:04 +02:00
Niels LohmannandGitHub 6ba332c7df Migrate remaining CI jobs off custom json-ci image to official images (#5263)
* Migrate ci_icpc/ci_test_compilers_gcc_old/ci_infer off custom json-ci image

Replaces the last three consumers of ghcr.io/nlohmann/json-ci with official
images: ci_icpc now uses Intel's own intel/oneapi-hpckit:2023.2.1-devel-ubuntu22.04
(the last release with classic icc/icpc before Intel dropped it in oneAPI
2024.0), ci_test_compilers_gcc_old installs old GCCs on official ubuntu:20.04
via the same PPA/archive setup the custom image used (working around
actions/checkout's incompatibility with official gcc:4/5/6 images), and
ci_infer runs directly on ubuntu-latest, fetching Facebook's official Infer
release tarball inline instead of a maintained image. No job in
ubuntu.yml references the custom image anymore.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Update quality-assurance compiler table for CI image migration

Reflects the ci_icpc/ci_test_compilers_gcc_old container migration: the
old-GCC jobs (4.8/4.9/5/6) now compile inside official ubuntu:20.04 rather
than the custom Focal-based json-ci image (same OS, just now attributed to
the official image), and ci_icpc now uses Intel's official
intel/oneapi-hpckit:2023.2.1-devel-ubuntu22.04, bumping the reported ICC
version from 2021.5.0 to 2021.10.0 and the OS from Ubuntu 20.04.3 to 22.04.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix CI failures from the json-ci image migration

- ci_icpc: the official intel/oneapi-hpckit image has no CMake preinstalled
  (the custom image bundled one); add the missing lukka/get-cmake step.
- ci_test_compilers_gcc_old: official ubuntu:20.04 has no build tool, so
  CMake's default Unix Makefiles generator failed with "CMAKE_MAKE_PROGRAM
  is not set"; install make alongside the PPA-provided g++.
- ci_infer: Infer v1.1.0's bundled Clang frontend can't parse GCC 14's
  headers (ubuntu-latest's default toolchain), failing with parse errors in
  <bits/unicode.h>; bump to the latest release, v1.3.0, whose newer bundled
  frontend understands them (release asset also renamed upstream from
  infer-linux64-v1.1.0.tar.xz to infer-linux-x86_64-v1.3.0.tar.xz).

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix ci_test_compilers_gcc_old: g++-6 missing from xenial-only archives

My inline PPA/archive replication only added the xenial main/universe
suites, but g++-6 isn't available there ("has no installation candidate").
The original custom Dockerfile also pulled from bionic main/universe and
xenial-updates main/universe; add those back to match.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix ci_test_compilers_gcc_old: install git for CMake's FetchContent tests

Official ubuntu:20.04 ships no git at all (actions/checkout only succeeded
via its API-download fallback). The cmake_fetch_content(2) tests invoke
CMake's own ExternalProject_Add, which needs a real git binary and failed
with "could not find git for clone of json-populate". Install git alongside
the other build prerequisites.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix ci_icpc: drop redundant setvars.sh sourcing

Unlike the old custom image, the official intel/oneapi-hpckit image already
has the oneAPI environment (icc/icpc on PATH) baked in at the container
level. Explicitly re-sourcing setvars.sh in the Build step failed with
"setvars.sh has already been run. Skipping re-execution." (exit code 3,
aborting the step under `sh -e`). Drop the now-unnecessary sourcing.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix ci_icpc: exclude classic ICC from the std::span regression test

Bumping to Intel's official intel/oneapi-hpckit:2023.2.1 image (see previous
commit) also bumped classic icc/icpc from 2021.5.0 to 2021.10.0. The newer
version's __has_include(<span>) now returns true, but it still can't
actually compile std::span/std::as_bytes usage:

  error: namespace "std" has no member "as_bytes"
  error: namespace "std" has no member "span"

Exclude __ICC/__INTEL_COMPILER the same way _LIBCPP_VERSION is already
excluded for issue #4490.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix amalgamation/style check: indent comment per astyle

Verified with the pinned astyle 3.4.13 (make install_astyle) locally;
no further diff.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Fix ci_icpc: skip UTF-8 u8-literal comparison test on classic ICC

test-deserialization_cpp20 failed:

  ERROR: CHECK( j2["emoji"] == "😀" ) is NOT correct!

check_utf8() only guards against MSVC's ANSI-codepage quirk (its docstring
example), but classic ICC has an analogous problem: it doesn't encode a
narrow string literal containing non-ASCII source characters as UTF-8,
so comparing a decoded u8R"(...)" literal against a narrow literal with
the same characters fails. Extend the existing guard.

Verified with the pinned astyle 3.4.13; no diff.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-10 16:11:41 +02:00
Niels LohmannandGitHub e9c3985f0a Fix documentation gaps found in a full GitHub Discussions review (#5264)
* 📝 Fix documentation gaps found in a full GitHub Discussions review

Reviewed all 1008 GitHub Discussions (2020-2026) for recurring questions
that better or more visible documentation would have avoided. Adds/expands
documentation for ~26 distinct gaps, including:

- New "Debugging" page collecting natvis, GDB pretty printer, LLDB status,
  and JSON_DIAGNOSTICS pointers (previously scattered/undiscoverable)
- Thread-safety and schema-validation FAQ entries
- StringType's char-based requirement (no wstring/u16string/u32string)
- Brace-initialization-yields-arrays warning directly on the constructor
  reference page (previously only in the FAQ, missed by users reading
  the constructor docs)
- std::any exclusion from get<T>(), with a manual-dispatch example
- Non-string-keyed std::map serializing as an array of pairs
- ordered_json compatibility with NLOHMANN_DEFINE_TYPE_* macros
  (already worked, was undocumented)
- std::array truncation on size-mismatched conversion (no exception)
- static_cast vs. get<std::optional<T>>() divergence
- Recipe for omitting a std::optional field instead of emitting null
- No built-in nesting-depth limit during parsing + a callback-based
  workaround recipe
- Recipe for streaming a large homogeneous array via parser callbacks
- operator>> stream-position semantics for concatenated JSON values
- JSON Pointer array-vs-object creation rule for non-existing paths
- CMake target name (nlohmann_json_modules) needed to link C++20 modules
- ESP-IDF/PlatformIO: no official package, link to a community fork
- get(key, default) as the Python dict.get() equivalent
- reserve() recipe for pre-allocating array capacity
- JSONC as an alias for the existing ignore_comments/ignore_trailing_commas
  combination (distinct from the unsupported JSON5)
- items() dereferenced-element type: decltype() idiom + detail-namespace
  stability caveat
- Various macro/type-conversion limitations (MSGPACK_DEFINE_ARRAY
  equivalent, char-array round-tripping, ADL serializer macro gap)

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* 🎨 fix format

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-10 16:01:08 +02:00
Niels LohmannandGitHub b630f5e9c7 Fix container input_adapter SFINAE for lvalue-only ADL begin/end (#5260)
* 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>

* Avoid strlen() in test container to fix Codacy CWE-126 flag

Suppressing the strlen()-based CWE-126 warning with NOLINT/nosec
comments only silenced clang-tidy and the standalone Flawfinder
Action; Codacy's own analysis (which also flags this pattern and
doesn't honor those suppression comments) still reported it as a new
issue, plus flagged the near-duplicate begin/end pair as cloned code.

Store the buffer's size explicitly in MyContainerNonConstADL instead
of computing it via strlen() in end(), which removes the flagged
pattern outright and also de-duplicates the struct from the existing
MyContainer's char*-based begin/end pair.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Avoid trailing return type to satisfy clang-tidy fuchsia-trailing-return

The forwarding-reference input_adapter(ContainerType&&) entry point was
written with an auto/trailing-decltype return type, but this project's
ci_clang_tidy job enables the fuchsia-trailing-return check as an
error, which rejects it. The return type only depends on the template
parameter ContainerType, not on the runtime parameter, so it can be
written as an ordinary leading return type instead - no functional
change.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Avoid C-style array in test to satisfy clang-tidy avoid-c-arrays

clang-tidy's cppcoreguidelines/hicpp/modernize-avoid-c-arrays checks
flagged the char raw_data[] declaration used to reproduce the
lvalue-only non-const ADL begin/end scenario. Use std::string instead
and take a mutable pointer via &raw_data[0], which is the standard
way to get a non-const char* into a string's buffer under C++11
(std::string::data() only returns non-const in C++17 and later).

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-10 13:56:06 +02:00
Niels Lohmann 4d8e7a7210 💚 fix build
Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-09 23:05:56 +02:00
Niels LohmannandGitHub 75e8fbac32 Documentation review: fix stale version-history placeholder in operator_ne.md (#5261)
* 📝 Fix stale 3.12.x placeholder in operator_ne.md version history

PR #5253 (removing the hand-written operator!= to fix #3868/P2468R2)
merged after the earlier 3.12.x -> 3.13.0 global sweep, so its new
version-history entries were written with the stale placeholder.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* 🐛 Fix stale twitter.com link in docset.json

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-09 20:57:41 +02:00
Niels LohmannandGitHub 631e667fe5 Document a duplicate-object-key rejection recipe (#5259)
* 📝 Document a duplicate-object-key rejection recipe

RFC 8259 leaves handling of duplicate object keys to the implementation;
this library silently keeps only the last value for a repeated key.
Discussion #5085 asked for an opt-in rejection mode. Decision: don't
change library behavior, but document the existing parser-callback
workaround instead.

Adds a "Recipe: rejecting duplicate object keys" section to
parser_callbacks.md, adapted from a community-contributed workaround.
Fixed an off-by-one bug in the original snippet: object_start reports
the depth of the object's parent, while key events inside that object
report depth+1, so indexing the per-depth key set with the same depth
in both places caused an out-of-bounds access on nested objects.
Verified the published snippet compiles and behaves correctly for flat
duplicates, nested duplicates, sibling objects sharing key names, and
arrays of objects.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Cross-link the duplicate-key recipe with the existing object_t behavior docs

object_t.md and features/types/index.md already document that duplicate
object keys resolve to an unspecified value (RFC 8259 leaves this to the
implementation). The new recipe's intro overstated this as a guaranteed
"last value wins" rule, which isn't true in general -- parsing text keeps
the last value, but constructing from an initializer list keeps the first.
Reworded the recipe to point at object_t's "unspecified" behavior instead
of asserting a specific rule, and added cross-links from both existing
pages to the new recipe.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* Turn the duplicate-key recipe into a standalone, compiled example

Replace the inline code fence in the "rejecting duplicate object keys"
recipe with a proper docs/mkdocs/docs/examples/*.cpp + .output pair,
included via --8<-- like every other example on the site. The .output
file was generated by running it through the project's actual example
build (docs/Makefile: single_include, -std=c++11, -DJSON_USE_GLOBAL_UDLS=0)
and cross-checked with `make check_output`, and the source passes the
pinned astyle 3.4.13 formatting unchanged.

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
2026-07-09 20:39:59 +02:00
d0a43141ea Fix #3868: Remove operator!= to enable P2468R2 rewritten candidate synthesis (#5253)
* Fix #3868: Remove operator!= to enable P2468R2 rewritten candidate synthesis

Under C++20 P2468R2, a hand-written operator!= suppresses the compiler's
rewritten-candidate synthesis for operator==, preventing heterogeneous
comparisons like `std::string s; json j; s == j;` from compiling.

Fix by removing the hand-written operator!=, allowing the compiler to
synthesize != as !(a==b) in all language modes (C++20 member functions
and pre-C++20 friend functions).

Behavior change: operator!= now returns !(a==b) unconditionally, including
for special values like NaN and discarded. This means:
- NaN != NaN now returns true (matches IEEE-754 semantics)
- discarded != x now returns true for any x (matches !(discarded == x))

This also fixes underlying defects in previously-working code:
- Restores direct == comparison for views vs json (reverts std::ranges::equal
  workaround added in PR #3950 to dodge this bug)
- Re-enables std::string == json comparisons (uncomments check in
  unit-constructor1.cpp)

Fixes: #3868, #3979

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Signed-off-by: Niels Lohmann <mail@nlohmann.me>

* 🚨 fix warning

Signed-off-by: Niels Lohmann <mail@nlohmann.me>

---------

Signed-off-by: Niels Lohmann <mail@nlohmann.me>
Co-authored-by: Claude Sonnet 5 <noreply@anthropic.com>
2026-07-09 20:38:39 +02:00