schemagen _CPP_KEYWORDS list is missing C++ keywords (mutable, wchar_t, char8_t, char16_t, char32_t, noexcept, typeid, *_cast, ...) — generated code does not compile
#62
contrib/schemagen/weaseljson_schemagen.py generates a C++ struct member whose name is a C++ keyword when a JSON Schema property key is one of several keywords that are absent from the _CPP_KEYWORDS allow-list. The generated header then fails to compile. This happens for perfectly valid JSON Schemas — JSON object keys may be any string, including ordinary words like "mutable" or type names like "wchar_t"/"char8_t".
This is distinct from the closed issue #18, which only added the C++20 keywords (concept, consteval, constinit, co_await, co_return, co_yield, requires, module, import). Many older C++ keywords were never added to the list and are still missing. It is also distinct from the open issues #59 (digit-leading names) and #60 (non-identifier characters).
Root cause
contrib/schemagen/weaseljson_schemagen.py, _CPP_KEYWORDS set (line 160) and sanitize() (line 111):
sanitize() only suffixes a name when it is a Python keyword or in _CPP_KEYWORDS. keyword.iskeyword only knows Python keywords, so C++-only keywords must be listed in _CPP_KEYWORDS. That set is missing many C++ keywords, including at least:
(not_eq is missing even though not is present; static_assert is missing even though static is present; static_cast is missing even though static is present.)
Compiling any TU that includes the header fails (GCC 16, -std=c++20):
gen.h:20:15: error: declaration does not declare anything [-fpermissive]
20 | std::string mutable; // "mutable"
| ^~~~~~~
gen.h:397:26: error: expected unqualified-id before 'mutable'
397 | case 0: return &o->mutable;
The same failure occurs for wchar_t, char8_t, char16_t, char32_t, noexcept, typeid, static_cast, xor, and_eq, compl, etc. (verified by generating a schema with each as the sole property key and running c++ -std=c++20 -fsyntax-only).
Expected behavior
sanitize() should append _ (e.g. mutable_) for every C++ keyword, the same way it already does for class, int, concept, etc., so the generated code compiles. Key matching (matchKey) compares against the original JSON key, so renaming only the C++ member is safe.
Impact
Schemas that use common words such as "mutable", or type-ish names such as "wchar_t"/"char8_t", as JSON property keys cannot be turned into compilable C++ structs. The failure is at C++ compile time of the generated header, after schemagen itself reported success (exit 0).
## Summary
`contrib/schemagen/weaseljson_schemagen.py` generates a C++ struct member whose name is a **C++ keyword** when a JSON Schema property key is one of several keywords that are absent from the `_CPP_KEYWORDS` allow-list. The generated header then fails to compile. This happens for perfectly valid JSON Schemas — JSON object keys may be any string, including ordinary words like `"mutable"` or type names like `"wchar_t"`/`"char8_t"`.
This is distinct from the closed issue #18, which only added the **C++20** keywords (`concept`, `consteval`, `constinit`, `co_await`, `co_return`, `co_yield`, `requires`, `module`, `import`). Many older C++ keywords were never added to the list and are still missing. It is also distinct from the open issues #59 (digit-leading names) and #60 (non-identifier characters).
## Root cause
`contrib/schemagen/weaseljson_schemagen.py`, `_CPP_KEYWORDS` set (line 160) and `sanitize()` (line 111):
```python
def sanitize(name, fallback="x"):
...
if keyword.iskeyword(s) or s in _CPP_KEYWORDS:
s = s + "_"
return s
```
`sanitize()` only suffixes a name when it is a Python keyword **or** in `_CPP_KEYWORDS`. `keyword.iskeyword` only knows Python keywords, so C++-only keywords must be listed in `_CPP_KEYWORDS`. That set is missing many C++ keywords, including at least:
`mutable`, `wchar_t`, `char8_t`, `char16_t`, `char32_t`, `noexcept`, `typeid`, `static_cast`, `dynamic_cast`, `reinterpret_cast`, `const_cast`, `static_assert`, `thread_local`, `and_eq`, `or_eq`, `xor`, `xor_eq`, `not_eq`, `bitand`, `bitor`, `compl`
(`not_eq` is missing even though `not` is present; `static_assert` is missing even though `static` is present; `static_cast` is missing even though `static` is present.)
## Reproduction
Minimal schema (`schema.json`):
```json
{"type":"object","additionalProperties":false,"properties":{"mutable":{"type":"string"}},"required":["mutable"]}
```
```sh
python3 contrib/schemagen/weaseljson_schemagen.py schema.json -o gen.h --namespace ts
```
schemagen exits 0 and emits (note `std::string mutable;` and `&o->mutable;`):
```cpp
struct Root1 {
std::string mutable; // "mutable"
};
...
case 0: return &o->mutable;
...
if (key == "mutable") return 0;
```
Compiling any TU that includes the header fails (GCC 16, `-std=c++20`):
```
gen.h:20:15: error: declaration does not declare anything [-fpermissive]
20 | std::string mutable; // "mutable"
| ^~~~~~~
gen.h:397:26: error: expected unqualified-id before 'mutable'
397 | case 0: return &o->mutable;
```
The same failure occurs for `wchar_t`, `char8_t`, `char16_t`, `char32_t`, `noexcept`, `typeid`, `static_cast`, `xor`, `and_eq`, `compl`, etc. (verified by generating a schema with each as the sole property key and running `c++ -std=c++20 -fsyntax-only`).
## Expected behavior
`sanitize()` should append `_` (e.g. `mutable_`) for every C++ keyword, the same way it already does for `class`, `int`, `concept`, etc., so the generated code compiles. Key matching (`matchKey`) compares against the original JSON key, so renaming only the C++ member is safe.
## Impact
Schemas that use common words such as `"mutable"`, or type-ish names such as `"wchar_t"`/`"char8_t"`, as JSON property keys cannot be turned into compilable C++ structs. The failure is at C++ compile time of the generated header, after schemagen itself reported success (exit 0).
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Summary
contrib/schemagen/weaseljson_schemagen.pygenerates a C++ struct member whose name is a C++ keyword when a JSON Schema property key is one of several keywords that are absent from the_CPP_KEYWORDSallow-list. The generated header then fails to compile. This happens for perfectly valid JSON Schemas — JSON object keys may be any string, including ordinary words like"mutable"or type names like"wchar_t"/"char8_t".This is distinct from the closed issue #18, which only added the C++20 keywords (
concept,consteval,constinit,co_await,co_return,co_yield,requires,module,import). Many older C++ keywords were never added to the list and are still missing. It is also distinct from the open issues #59 (digit-leading names) and #60 (non-identifier characters).Root cause
contrib/schemagen/weaseljson_schemagen.py,_CPP_KEYWORDSset (line 160) andsanitize()(line 111):sanitize()only suffixes a name when it is a Python keyword or in_CPP_KEYWORDS.keyword.iskeywordonly knows Python keywords, so C++-only keywords must be listed in_CPP_KEYWORDS. That set is missing many C++ keywords, including at least:mutable,wchar_t,char8_t,char16_t,char32_t,noexcept,typeid,static_cast,dynamic_cast,reinterpret_cast,const_cast,static_assert,thread_local,and_eq,or_eq,xor,xor_eq,not_eq,bitand,bitor,compl(
not_eqis missing even thoughnotis present;static_assertis missing even thoughstaticis present;static_castis missing even thoughstaticis present.)Reproduction
Minimal schema (
schema.json):schemagen exits 0 and emits (note
std::string mutable;and&o->mutable;):Compiling any TU that includes the header fails (GCC 16,
-std=c++20):The same failure occurs for
wchar_t,char8_t,char16_t,char32_t,noexcept,typeid,static_cast,xor,and_eq,compl, etc. (verified by generating a schema with each as the sole property key and runningc++ -std=c++20 -fsyntax-only).Expected behavior
sanitize()should append_(e.g.mutable_) for every C++ keyword, the same way it already does forclass,int,concept, etc., so the generated code compiles. Key matching (matchKey) compares against the original JSON key, so renaming only the C++ member is safe.Impact
Schemas that use common words such as
"mutable", or type-ish names such as"wchar_t"/"char8_t", as JSON property keys cannot be turned into compilable C++ structs. The failure is at C++ compile time of the generated header, after schemagen itself reported success (exit 0).