Skip to content

Commit

Permalink
Correctly serialize Strings in XML (#1832)
Browse files Browse the repository at this point in the history
The logic that keeps track of whether we're working with a borrowed or
an owned value is flawed. It just so happened to work when requesting
owned values from borrowed values because we called `autoDeref` before
creating the value expression. That logic should instead be used
_within_ `ValueExpression` to appease Clippy there too.

Fixes #1831.
  • Loading branch information
david-perez authored Oct 13, 2022
1 parent 7866477 commit aa60bad
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 9 deletions.
15 changes: 14 additions & 1 deletion codegen-client-test/model/rest-xml-extras.smithy
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ service RestXmlExtras {
ChecksumRequired,
StringHeader,
CreateFoo,
RequiredMember,
]
}

Expand Down Expand Up @@ -242,5 +243,17 @@ structure StringHeaderOutput {
field: String,

@httpHeader("x-enum")
enumHeader: StringEnum
enumHeader: StringEnum,
}

/// This operation tests that we can serialize `required` members.
@http(uri: "/required-member", method: "GET")
operation RequiredMember {
input: RequiredMemberInputOutput
output: RequiredMemberInputOutput
}

structure RequiredMemberInputOutput {
@required
requiredString: String
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,16 @@

package software.amazon.smithy.rust.codegen.core.smithy.protocols.serialize

import software.amazon.smithy.rust.codegen.core.rustlang.autoDeref

sealed class ValueExpression {
abstract val name: String

data class Reference(override val name: String) : ValueExpression()
data class Value(override val name: String) : ValueExpression()

fun asValue(): String = when (this) {
is Reference -> "*$name"
is Reference -> autoDeref(name)
is Value -> name
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@ import software.amazon.smithy.model.shapes.StringShape
import software.amazon.smithy.model.shapes.StructureShape
import software.amazon.smithy.model.shapes.TimestampShape
import software.amazon.smithy.model.shapes.UnionShape
import software.amazon.smithy.model.traits.EnumTrait
import software.amazon.smithy.model.traits.TimestampFormatTrait
import software.amazon.smithy.model.traits.XmlFlattenedTrait
import software.amazon.smithy.model.traits.XmlNamespaceTrait
Expand Down Expand Up @@ -285,11 +284,9 @@ class XmlBindingTraitSerializerGenerator(
}

private fun RustWriter.serializeRawMember(member: MemberShape, input: String) {
when (val shape = model.expectShape(member.target)) {
is StringShape -> if (shape.hasTrait<EnumTrait>()) {
when (model.expectShape(member.target)) {
is StringShape -> {
rust("$input.as_str()")
} else {
rust("$input.as_ref()")
}
is BooleanShape, is NumberShape -> {
rust(
Expand Down Expand Up @@ -444,7 +441,7 @@ class XmlBindingTraitSerializerGenerator(
* ```
*
* If [member] is not an optional shape, generate code like:
* `{ .. Block }`
* `{ .. BLOCK }`
*
* [inner] is passed a new `ctx` object to use for code generation which handles the
* potentially new name of the input.
Expand All @@ -462,7 +459,12 @@ class XmlBindingTraitSerializerGenerator(
}
} else {
with(util) {
ignoreZeroValues(member, ValueExpression.Value(autoDeref(ctx.input))) {
val valueExpression = if (ctx.input.startsWith("&")) {
ValueExpression.Reference(ctx.input)
} else {
ValueExpression.Value(ctx.input)
}
ignoreZeroValues(member, valueExpression) {
inner(ctx)
}
}
Expand Down

0 comments on commit aa60bad

Please sign in to comment.