OpenAPITools/openapi-generator · error · IllegalArgumentException
property %s in model %s cannot use %s as its public Python n
Error message
property %s in model %s cannot use %s as its public Python name
What it means
The python generator validates any explicitly mapped public name (--name-mapping) against Python identifier rules: it must match [A-Za-z_][A-Za-z0-9_]*, must not be a Python keyword, and must not start with '__' (dunder names are reserved for the generated class machinery). Violations throw this IllegalArgumentException during model post-processing.
Source
Thrown at modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/PythonClientCodegen.java:835
|| legacyMetadataCollision
|| nameMappingGeneratedMembers.contains(publicName));
boolean storageNameCollision = generatedMembers.contains(property.name)
&& (explicitPublicName
|| legacyMetadataCollision
|| nameMappingGeneratedMembers.contains(property.name));
if (publicNameCollision || storageNameCollision) {
String generatedMemberName = publicNameCollision
? publicName
: property.name;
throw new IllegalArgumentException(String.format(Locale.ROOT,
"property %s in model %s uses generated Python member name %s",
property.baseName, model.name, generatedMemberName));
}
if (explicitPublicName
&& (!publicName.matches("[A-Za-z_][A-Za-z0-9_]*")
|| PYTHON_KEYWORDS.contains(publicName)
|| publicName.startsWith("__"))) {
throw new IllegalArgumentException(String.format(Locale.ROOT,
"property %s in model %s cannot use %s as its public Python name",
property.baseName, model.name, publicName));
}
if (explicitPublicName
&& (!property.name.matches("[A-Za-z][A-Za-z0-9_]*")
|| PYTHON_KEYWORDS.contains(property.name)
|| MODEL_FIELD_NAME_COLLISIONS.contains(property.name)
|| MODEL_CLASS_BODY_NAMES.contains(property.name)
|| PYDANTIC_PRIVATE_MEMBER_NAMES.contains(property.name))) {
throw new IllegalArgumentException(String.format(Locale.ROOT,
"property %s in model %s has invalid generated Python field name %s",
property.baseName, model.name, property.name));
}
for (String inputName : List.of(property.baseName, publicName)) {
CodegenProperty owner = inputNameOwners.putIfAbsent(inputName, property);
if (owner != null
&& !owner.baseName.equals(property.baseName)View on GitHub (pinned to fcec517be3)
Solutions
- Choose a target name that starts with a letter or single underscore, contains only [A-Za-z0-9_], and is not a Python keyword
- Remove the leading '__' (e.g. use _private or private_)
- Rename the property in the spec instead of mapping it to an invalid identifier
Example fix
# before openapi-generator-cli generate -i api.yaml -g python --name-mapping order_id=1st_order,class_type=class # after openapi-generator-cli generate -i api.yaml -g python --name-mapping order_id=first_order,class_type=clazz
Defensive patterns
Strategy: validation
Validate before calling
# Validate a mapping target as a Python public identifier (Python):
import keyword
PUBLIC_RE = re.compile(r'^[A-Za-z_][A-Za-z0-9_]*$')
def valid_public(name: str) -> bool:
return bool(PUBLIC_RE.match(name)) and not keyword.iskeyword(name) and not name.startswith('__')
assert all(valid_public(t) for t in mapping_targets) Try / catch
try {
new DefaultGenerator().opts(input).generate();
} catch (IllegalArgumentException e) {
// message: 'property X in model Y cannot use Z as its public Python name'
// change the --name-mapping target to a valid identifier and rerun
} Prevention
- Keep a regex+keyword check for public names in your mapping authoring workflow
- Never start public names with '__'; single '_' is allowed but avoid it for public API
- Automate mapping generation from a reviewed list rather than hand-editing per property
When it happens
Trigger: -g python --name-mapping foo=1st_choice (starts with digit), foo=__private (dunder prefix), foo=class / foo=return (keyword), foo=two words (space) or foo=empty-string.
Common situations: Mapping wire names to human-friendly labels that contain spaces, hyphens, or leading digits; teams converting camelCase APIs to Python style and picking names like 'from' or 'type' without realizing they are keywords.
Related errors
- property %s in model %s has invalid generated Python field n
- property %s in model %s uses generated Python member name %s
- properties %s and %s in model %s both accept input name %s
- properties %s and %s in model %s both use Python member name
- property %s in model %s uses generated storage name %s, whic
AI-assisted analysis of OpenAPITools/openapi-generator@fcec517be3 (2026-08-22).
Data as JSON: /api/errors/a8d3d4bc465cda48.
Report an issue: GitHub.