Skip to content

Commit 6d90db5

Browse files
authored
fix: fixes s3 decode compiler errors (#395)
1 parent d23a558 commit 6d90db5

File tree

5 files changed

+205
-188
lines changed

5 files changed

+205
-188
lines changed

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/serde/xml/MemberShapeDecodeXMLGenerator.kt

Lines changed: 66 additions & 80 deletions
Original file line numberDiff line numberDiff line change
@@ -39,55 +39,46 @@ abstract class MemberShapeDecodeXMLGenerator(
3939
abstract fun renderAssigningDecodedMember(memberName: String, decodedMemberName: String, isBoxed: Boolean = false)
4040
abstract fun renderAssigningSymbol(memberName: String, symbol: String)
4141
abstract fun renderAssigningNil(memberName: String)
42+
abstract fun renderListMember(member: MemberShape, memberTarget: CollectionShape, containerName: String)
43+
abstract fun renderMapMember(member: MemberShape, memberTarget: MapShape, containerName: String)
4244

43-
fun renderListMember(
44-
member: MemberShape,
45-
memberTarget: CollectionShape,
46-
containerName: String
47-
) {
48-
val memberName = ctx.symbolProvider.toMemberName(member).removeSurrounding("`", "`")
45+
fun renderListMember(memberName: String, containerName: String, member: MemberShape, memberTarget: CollectionShape) {
4946
val memberIsFlattened = member.hasTrait(XmlFlattenedTrait::class.java)
5047
var currContainerName = containerName
5148
var currContainerKey = ".$memberName"
49+
var containerUsedForDecoding: String
50+
var ifNilOrIfLetStatement: String
51+
val nextContainerName = "${memberName}WrappedContainer"
52+
if (!memberIsFlattened) {
53+
val memberCodingKey = CollectionMemberCodingKey.construct(memberTarget.member)
54+
memberCodingKey.renderStructs(writer)
55+
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: CollectionMemberCodingKey<${memberCodingKey.keyTag()}>.CodingKeys.self, forKey: $currContainerKey)")
56+
currContainerKey = ".member"
57+
currContainerName = nextContainerName
58+
containerUsedForDecoding = currContainerName
59+
ifNilOrIfLetStatement = "if let $currContainerName = $currContainerName {"
60+
} else {
61+
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: CodingKeys.self, forKey: $currContainerKey)")
62+
// currContainerKey is intentionally not updated. This container is only used to detect empty lists, not for decoding.
63+
currContainerName = nextContainerName
64+
containerUsedForDecoding = containerName
65+
ifNilOrIfLetStatement = "if $currContainerName != nil {"
66+
}
5267

53-
writer.openBlock("if $containerName.contains(.$memberName) {", "} else {") {
54-
var containerUsedForDecoding: String
55-
var ifNilOrIfLetStatement: String
56-
val nextContainerName = "${memberName}WrappedContainer"
57-
if (!memberIsFlattened) {
58-
val memberCodingKey = CollectionMemberCodingKey.construct(memberTarget.member)
59-
memberCodingKey.renderStructs(writer)
60-
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: CollectionMemberCodingKey<${memberCodingKey.keyTag()}>.CodingKeys.self, forKey: $currContainerKey)")
61-
currContainerKey = ".member"
62-
currContainerName = nextContainerName
63-
containerUsedForDecoding = currContainerName
64-
ifNilOrIfLetStatement = "if let $currContainerName = $currContainerName {"
65-
} else {
66-
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: CodingKeys.self, forKey: $currContainerKey)")
67-
// currContainerKey is intentionally not updated. This container is only used to detect empty lists, not for decoding.
68-
currContainerName = nextContainerName
69-
containerUsedForDecoding = containerName
70-
ifNilOrIfLetStatement = "if $currContainerName != nil {"
71-
}
72-
73-
writer.openBlock(ifNilOrIfLetStatement, "} else {") {
74-
val memberBuffer = "${memberName}Buffer"
75-
val memberContainerName = "${memberName}Container"
76-
val (memberTargetSymbol, memberTargetSymbolName) = nestedMemberTargetSymbolMapper(memberTarget)
77-
writer.write("let $memberContainerName = try $containerUsedForDecoding.decodeIfPresent($memberTargetSymbolName.self, forKey: $currContainerKey)")
78-
writer.write("var $memberBuffer:\$T = nil", memberTargetSymbol)
79-
writer.openBlock("if let $memberContainerName = $memberContainerName {", "}") {
80-
writer.write("$memberBuffer = \$N()", memberTargetSymbol)
81-
renderListMemberItems(memberTarget, memberContainerName, memberBuffer)
82-
}
83-
renderAssigningDecodedMember(memberName, memberBuffer)
68+
writer.openBlock(ifNilOrIfLetStatement, "} else {") {
69+
val memberBuffer = "${memberName}Buffer"
70+
val memberContainerName = "${memberName}Container"
71+
val (memberTargetSymbol, memberTargetSymbolName) = nestedMemberTargetSymbolMapper(memberTarget)
72+
writer.write("let $memberContainerName = try $containerUsedForDecoding.decodeIfPresent($memberTargetSymbolName.self, forKey: $currContainerKey)")
73+
writer.write("var $memberBuffer:\$T = nil", memberTargetSymbol)
74+
writer.openBlock("if let $memberContainerName = $memberContainerName {", "}") {
75+
writer.write("$memberBuffer = \$N()", memberTargetSymbol)
76+
renderListMemberItems(memberTarget, memberContainerName, memberBuffer)
8477
}
85-
writer.indent()
86-
renderAssigningSymbol(memberName, "[]")
87-
writer.dedent().write("}")
78+
renderAssigningDecodedMember(memberName, memberBuffer)
8879
}
8980
writer.indent()
90-
renderAssigningNil(memberName)
81+
renderAssigningSymbol(memberName, "[]")
9182
writer.dedent().write("}")
9283
}
9384

@@ -157,53 +148,47 @@ abstract class MemberShapeDecodeXMLGenerator(
157148
}
158149
}
159150

160-
fun renderMapMember(member: MemberShape, memberTarget: MapShape, containerName: String) {
151+
fun renderMapMember(member: MemberShape, memberTarget: MapShape, containerName: String, memberName: String) {
161152
val memberTargetValue = ctx.symbolProvider.toSymbol(memberTarget.value)
162153
val symbolOptional = if (ctx.symbolProvider.toSymbol(memberTarget).isBoxed()) "?" else ""
163154

164-
val memberName = ctx.symbolProvider.toMemberName(member)
165155
val memberNameUnquoted = memberName.removeSurrounding("`", "`")
166156
var currContainerName = containerName
167157
var currContainerKey = ".$memberNameUnquoted"
168158
val memberIsFlattened = member.hasTrait<XmlFlattenedTrait>()
169-
writer.openBlock("if $containerName.contains(.$memberName) {", "} else {") {
170-
val keyedBySymbolForContainer = determineSymbolForShapeInMap(memberTarget, ClientRuntimeTypes.Serde.MapEntry, true)
171-
var containerUsedForDecoding: String
172-
var ifNilOrIfLetStatement: String
173-
val nextContainerName = "${memberNameUnquoted}WrappedContainer"
174-
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: $keyedBySymbolForContainer.CodingKeys.self, forKey: $currContainerKey)")
175-
if (!memberIsFlattened) {
176-
currContainerKey = ".entry"
177-
currContainerName = nextContainerName
178-
containerUsedForDecoding = currContainerName
179-
ifNilOrIfLetStatement = "if let $currContainerName = $currContainerName {"
180-
} else {
181-
// currContainerKey is intentionally not updated. This container is only used to detect empty lists, not for decoding.
182-
currContainerName = nextContainerName
183-
containerUsedForDecoding = containerName
184-
ifNilOrIfLetStatement = "if $currContainerName != nil {"
185-
}
159+
val keyedBySymbolForContainer = determineSymbolForShapeInMap(memberTarget, ClientRuntimeTypes.Serde.MapEntry, true)
160+
var containerUsedForDecoding: String
161+
var ifNilOrIfLetStatement: String
162+
val nextContainerName = "${memberNameUnquoted}WrappedContainer"
163+
writer.write("let $nextContainerName = $currContainerName.nestedContainerNonThrowable(keyedBy: $keyedBySymbolForContainer.CodingKeys.self, forKey: $currContainerKey)")
164+
if (!memberIsFlattened) {
165+
currContainerKey = ".entry"
166+
currContainerName = nextContainerName
167+
containerUsedForDecoding = currContainerName
168+
ifNilOrIfLetStatement = "if let $currContainerName = $currContainerName {"
169+
} else {
170+
// currContainerKey is intentionally not updated. This container is only used to detect empty lists, not for decoding.
171+
currContainerName = nextContainerName
172+
containerUsedForDecoding = containerName
173+
ifNilOrIfLetStatement = "if $currContainerName != nil {"
174+
}
186175

187-
writer.openBlock(ifNilOrIfLetStatement, "} else {") {
188-
val memberBuffer = "${memberNameUnquoted}Buffer"
189-
val memberContainerName = "${memberNameUnquoted}Container"
190-
val memberTargetSymbol = "[${SwiftTypes.String}:$memberTargetValue]"
176+
writer.openBlock(ifNilOrIfLetStatement, "} else {") {
177+
val memberBuffer = "${memberNameUnquoted}Buffer"
178+
val memberContainerName = "${memberNameUnquoted}Container"
179+
val memberTargetSymbol = "[${SwiftTypes.String}:$memberTargetValue]"
191180

192-
val symbolToDecodeTo = determineSymbolForShapeInMap(memberTarget, ClientRuntimeTypes.Serde.MapKeyValue, false)
193-
writer.write("let $memberContainerName = try $containerUsedForDecoding.decodeIfPresent([$symbolToDecodeTo].self, forKey: $currContainerKey)")
194-
writer.write("var $memberBuffer: ${memberTargetSymbol}$symbolOptional = nil")
195-
writer.openBlock("if let $memberContainerName = $memberContainerName {", "}") {
196-
writer.write("$memberBuffer = $memberTargetSymbol()")
197-
renderMapMemberItems(memberTarget.value, memberContainerName, memberBuffer)
198-
}
199-
renderAssigningDecodedMember(memberName, memberBuffer)
181+
val symbolToDecodeTo = determineSymbolForShapeInMap(memberTarget, ClientRuntimeTypes.Serde.MapKeyValue, false)
182+
writer.write("let $memberContainerName = try $containerUsedForDecoding.decodeIfPresent([$symbolToDecodeTo].self, forKey: $currContainerKey)")
183+
writer.write("var $memberBuffer: ${memberTargetSymbol}$symbolOptional = nil")
184+
writer.openBlock("if let $memberContainerName = $memberContainerName {", "}") {
185+
writer.write("$memberBuffer = $memberTargetSymbol()")
186+
renderMapMemberItems(memberTarget.value, memberContainerName, memberBuffer)
200187
}
201-
writer.indent()
202-
renderAssigningSymbol(memberName, "[:]")
203-
writer.dedent().write("}")
188+
renderAssigningDecodedMember(memberName, memberBuffer)
204189
}
205190
writer.indent()
206-
renderAssigningNil(memberName)
191+
renderAssigningSymbol(memberName, "[:]")
207192
writer.dedent().write("}")
208193
}
209194

@@ -249,7 +234,7 @@ abstract class MemberShapeDecodeXMLGenerator(
249234
}
250235
}
251236

252-
fun renderTimestampMember(member: MemberShape, memberTarget: TimestampShape, containerName: String) {
237+
open fun renderTimestampMember(member: MemberShape, memberTarget: TimestampShape, containerName: String) {
253238
val memberName = ctx.symbolProvider.toMemberName(member).removeSurrounding("`", "`")
254239
var memberTargetSymbol = ctx.symbolProvider.toSymbol(memberTarget)
255240
val decodeVerb = if (memberTargetSymbol.isBoxed()) "decodeIfPresent" else "decode"
@@ -265,14 +250,15 @@ abstract class MemberShapeDecodeXMLGenerator(
265250
renderAssigningDecodedMember(memberName, memberBuffer)
266251
}
267252

268-
fun renderBlobMember(member: MemberShape, memberTarget: BlobShape, containerName: String) {
253+
open fun renderBlobMember(member: MemberShape, memberTarget: BlobShape, containerName: String) {
269254
val memberName = ctx.symbolProvider.toMemberName(member)
270255
val memberNameUnquoted = memberName.removeSurrounding("`", "`")
271256
var memberTargetSymbol = ctx.symbolProvider.toSymbol(memberTarget)
272257
if (member.hasTrait(SwiftBoxTrait::class.java)) {
273258
memberTargetSymbol = memberTargetSymbol.recursiveSymbol()
274259
}
275260
val decodedMemberName = "${memberName}Decoded"
261+
276262
writer.openBlock("if $containerName.contains(.$memberNameUnquoted) {", "} else {") {
277263
writer.openBlock("do {", "} catch {") {
278264
writer.write("let $decodedMemberName = try $containerName.decodeIfPresent(\$N.self, forKey: .$memberNameUnquoted)", memberTargetSymbol)
@@ -293,14 +279,14 @@ abstract class MemberShapeDecodeXMLGenerator(
293279
renderAssigningDecodedMember(memberName, "$value")
294280
}
295281

296-
fun renderScalarMember(member: MemberShape, memberTarget: Shape, containerName: String, unkeyed: Boolean = false) {
282+
fun renderScalarMember(member: MemberShape, memberTarget: Shape, containerName: String, unkeyed: Boolean = false, isUnion: Boolean = false) {
297283
val memberName = ctx.symbolProvider.toMemberName(member)
298284
val memberNameUnquoted = memberName.removeSurrounding("`", "`")
299285
var memberTargetSymbol = ctx.symbolProvider.toSymbol(memberTarget)
300286
if (member.hasTrait(SwiftBoxTrait::class.java)) {
301287
memberTargetSymbol = memberTargetSymbol.recursiveSymbol()
302288
}
303-
val decodeVerb = if (memberTargetSymbol.isBoxed()) "decodeIfPresent" else "decode"
289+
val decodeVerb = if (memberTargetSymbol.isBoxed() && !isUnion) "decodeIfPresent" else "decode"
304290
val decodedMemberName = "${memberNameUnquoted}Decoded"
305291
if (unkeyed) {
306292
writer.write("let $decodedMemberName = try $containerName.$decodeVerb(\$N.self)", memberTargetSymbol)

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/serde/xml/StructDecodeXMLGenerator.kt

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,26 @@ open class StructDecodeXMLGenerator(
6161
}
6262
}
6363

64+
override fun renderListMember(member: MemberShape, memberTarget: CollectionShape, containerName: String) {
65+
val memberName = ctx.symbolProvider.toMemberName(member).removeSurrounding("`", "`")
66+
writer.openBlock("if $containerName.contains(.$memberName) {", "} else {") {
67+
renderListMember(memberName, containerName, member, memberTarget)
68+
}
69+
writer.indent()
70+
renderAssigningNil(memberName)
71+
writer.dedent().write("}")
72+
}
73+
74+
override fun renderMapMember(member: MemberShape, memberTarget: MapShape, containerName: String) {
75+
val memberName = ctx.symbolProvider.toMemberName(member)
76+
writer.openBlock("if $containerName.contains(.$memberName) {", "} else {") {
77+
renderMapMember(member, memberTarget, containerName, memberName)
78+
}
79+
writer.indent()
80+
renderAssigningNil(memberName)
81+
writer.dedent().write("}")
82+
}
83+
6484
override fun renderAssigningDecodedMember(memberName: String, decodedMemberName: String, isBoxed: Boolean) {
6585
writer.write("$memberName = $decodedMemberName")
6686
}

0 commit comments

Comments
 (0)