Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index = 0; index < attributeTypes.length; index++) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,10 @@ export class ObjectSerializer {
let attributeTypes = typeMap[type].getAttributeTypeMap();
let instance: {[index: string]: any} = {};
for (let attributeType of attributeTypes) {
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type, attributeType.format);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
Comment on lines +208 to +210

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: When the same object carries both the sanitized name key and the raw baseName key with different values, this reads data[name] first and silently drops the baseName value. That happens with property-name collisions, which the generator produces: a legal field foo_bar gets name = "foo_bar", while an illegal field foo-bar is sanitized to the same name = "foo_bar" (see toVarName/sanitizeName in TypeScriptClientCodegen). The lookup on attributeType.name is then satisfied by the other field's value and serialized under foo-bar, emitting incorrect data. Since serialize outputs under attributeType.baseName, prefer the baseName key and fall back to name, which also matches the wire-format key and both file patterns for consistency.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/resources/typescript/model/ObjectSerializer.mustache, line 208:

<comment>When the same object carries both the sanitized `name` key and the raw `baseName` key with different values, this reads `data[name]` first and silently drops the `baseName` value. That happens with property-name collisions, which the generator produces: a legal field `foo_bar` gets `name = "foo_bar"`, while an illegal field `foo-bar` is sanitized to the same `name = "foo_bar"` (see `toVarName`/`sanitizeName` in `TypeScriptClientCodegen`). The lookup on `attributeType.name` is then satisfied by the other field's value and serialized under `foo-bar`, emitting incorrect data. Since `serialize` outputs under `attributeType.baseName`, prefer the `baseName` key and fall back to `name`, which also matches the wire-format key and both file patterns for consistency.</comment>

<file context>
@@ -205,7 +205,10 @@ export class ObjectSerializer {
             let instance: {[index: string]: any} = {};
             for (let attributeType of attributeTypes) {
-                instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type, attributeType.format);
+                const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
+                    ? data[attributeType.name]
+                    : data[attributeType.baseName];
</file context>
Suggested change
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
const value = Object.prototype.hasOwnProperty.call(data, attributeType.baseName)
? data[attributeType.baseName]
: data[attributeType.name];

instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type, attributeType.format);
}
return instance;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index in attributeTypes) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index = 0; index < attributeTypes.length; index++) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 4 additions & 1 deletion samples/client/petstore/typescript-node/3_0/model/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index = 0; index < attributeTypes.length; index++) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index = 0; index < attributeTypes.length; index++) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down
5 changes: 4 additions & 1 deletion samples/client/petstore/typescript-node/npm/model/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,10 @@ export class ObjectSerializer {
let instance: {[index: string]: any} = {};
for (let index = 0; index < attributeTypes.length; index++) {
let attributeType = attributeTypes[index];
instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
const value = Object.prototype.hasOwnProperty.call(data, attributeType.name)
? data[attributeType.name]
: data[attributeType.baseName];
instance[attributeType.baseName] = ObjectSerializer.serialize(value, attributeType.type);
}
return instance;
}
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading