Skip to content

Commit 3078404

Browse files
authored
feat: add support for unbound event stream payloads (#690)
1 parent 1ffaf31 commit 3078404

File tree

4 files changed

+45
-2
lines changed

4 files changed

+45
-2
lines changed
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"id": "704b9a6e-d859-4706-b39f-91052b375834",
3+
"type": "misc",
4+
"description": "Add unbound event stream payload deserialization path"
5+
}

codegen/smithy-aws-kotlin-codegen/src/main/kotlin/aws/sdk/kotlin/codegen/protocols/eventstream/EventStreamParserGenerator.kt

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -150,8 +150,14 @@ class EventStreamParserGenerator(
150150
} else {
151151
if (unbound.isNotEmpty()) {
152152
// all remaining members are bound to payload (but not explicitly bound via @eventPayload)
153-
// FIXME - this would require us to generate a "partial" deserializer like we do for where the builder is passed in
154-
TODO("support for unbound event stream members is not implemented")
153+
// generate a payload deserializer specific to the unbound members (note this will be a deserializer
154+
// for the overall event shape but only payload members will be considered for deserialization),
155+
// and then assign each deserialized payload member to the current builder instance
156+
val payloadDeserializeFn = sdg.payloadDeserializer(ctx, member, unbound)
157+
writer.write("val tmp = #T(message.payload)", payloadDeserializeFn)
158+
unbound.forEach {
159+
writer.write("eb.#1L = tmp.#1L", it.defaultName())
160+
}
155161
}
156162
}
157163

tests/codegen/event-stream/event-stream-model-template.smithy

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,11 @@ structure MessageWithNoHeaderPayloadTraits {
6464
someString: String,
6565
}
6666

67+
structure MessageWithUnboundPayloadTraits {
68+
@eventHeader header: String,
69+
unboundString: String,
70+
}
71+
6772
@streaming
6873
union TestStream {
6974
MessageWithBlob: MessageWithBlob,
@@ -73,5 +78,6 @@ union TestStream {
7378
MessageWithHeaders: MessageWithHeaders,
7479
MessageWithHeaderAndPayload: MessageWithHeaderAndPayload,
7580
MessageWithNoHeaderPayloadTraits: MessageWithNoHeaderPayloadTraits,
81+
MessageWithUnboundPayloadTraits: MessageWithUnboundPayloadTraits,
7682
SomeError: SomeError,
7783
}

tests/codegen/event-stream/src/test/kotlin/EventStreamTests.kt

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -237,4 +237,30 @@ class EventStreamTests {
237237
assertIs<TestStream.MessageWithNoHeaderPayloadTraits>(deserialized)
238238
assertEquals(event, deserialized)
239239
}
240+
241+
@Test
242+
fun testSerializeMessageWithUnboundPayload() = runTest {
243+
val event = TestStream.MessageWithUnboundPayloadTraits(
244+
MessageWithUnboundPayloadTraits {
245+
header = "a korf is a tiger"
246+
unboundString = "a flix is comb"
247+
},
248+
)
249+
250+
val message = serializedMessage(event)
251+
252+
val headers = message.headers.associate { it.name to it.value }
253+
assertEquals("event", headers[":message-type"]?.expectString())
254+
assertEquals("MessageWithUnboundPayloadTraits", headers[":event-type"]?.expectString())
255+
assertEquals("application/json", headers[":content-type"]?.expectString())
256+
257+
assertEquals("a korf is a tiger", headers["header"]?.expectString())
258+
259+
val expectedBody = """{"unboundString":"a flix is comb"}"""
260+
assertJsonStringsEqual(expectedBody, message.payload.decodeToString())
261+
262+
val deserialized = deserializedEvent(message)
263+
assertIs<TestStream.MessageWithUnboundPayloadTraits>(deserialized)
264+
assertEquals(event, deserialized)
265+
}
240266
}

0 commit comments

Comments
 (0)