Skip to content

Commit 226c54c

Browse files
authored
fix: remove duplicated middlewares (#400)
1 parent 0faded8 commit 226c54c

20 files changed

+240
-310
lines changed
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
//
2+
// Copyright Amazon.com Inc. or its affiliates.
3+
// All Rights Reserved.
4+
//
5+
// SPDX-License-Identifier: Apache-2.0
6+
//
7+
8+
public struct SerializableBodyMiddleware<OperationStackInput: Encodable & Reflection,
9+
OperationStackOutput: HttpResponseBinding,
10+
OperationStackError: HttpResponseBinding>: Middleware {
11+
public let id: Swift.String = "\(String(describing: OperationStackInput.self))BodyMiddleware"
12+
13+
let alwaysSendBody: Bool
14+
15+
public init(alwaysSendBody: Bool = false) {
16+
self.alwaysSendBody = alwaysSendBody
17+
}
18+
19+
public func handle<H>(context: Context,
20+
input: SerializeStepInput<OperationStackInput>,
21+
next: H) -> Swift.Result<OperationOutput<OperationStackOutput>, MError>
22+
where H: Handler,
23+
Self.MInput == H.Input,
24+
Self.MOutput == H.Output,
25+
Self.Context == H.Context,
26+
Self.MError == H.MiddlewareError {
27+
do {
28+
if try alwaysSendBody || !input.operationInput.allPropertiesAreNull() {
29+
let encoder = context.getEncoder()
30+
let data = try encoder.encode(input.operationInput)
31+
let body = HttpBody.data(data)
32+
input.builder.withBody(body)
33+
}
34+
} catch let err {
35+
return .failure(.client(ClientError.serializationFailed(err.localizedDescription)))
36+
}
37+
return next.handle(context: context, input: input)
38+
}
39+
40+
public typealias MInput = SerializeStepInput<OperationStackInput>
41+
public typealias MOutput = OperationOutput<OperationStackOutput>
42+
public typealias Context = HttpContext
43+
public typealias MError = SdkError<OperationStackError>
44+
}
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
//
2+
// Copyright Amazon.com Inc. or its affiliates.
3+
// All Rights Reserved.
4+
//
5+
// SPDX-License-Identifier: Apache-2.0
6+
//
7+
8+
public struct URLHostMiddleware<OperationStackInput: Encodable & Reflection,
9+
OperationStackOutput: HttpResponseBinding,
10+
OperationStackError: HttpResponseBinding>: Middleware {
11+
public let id: String = "\(String(describing: OperationStackInput.self))URLHostMiddleware"
12+
13+
let host: String?
14+
let hostPrefix: String?
15+
16+
public init(host: String? = nil, hostPrefix: String? = nil) {
17+
self.host = host
18+
self.hostPrefix = hostPrefix
19+
}
20+
21+
public func handle<H>(context: Context,
22+
input: MInput,
23+
next: H) -> Result<MOutput, MError>
24+
where H: Handler,
25+
Self.MInput == H.Input,
26+
Self.MOutput == H.Output,
27+
Self.Context == H.Context,
28+
Self.MError == H.MiddlewareError {
29+
var copiedContext = context
30+
if let host = host {
31+
copiedContext.attributes.set(key: AttributeKey<String>(name: "Host"),
32+
value: host)
33+
}
34+
if let hostPrefix = hostPrefix {
35+
copiedContext.attributes.set(key: AttributeKey<String>(name: "HostPrefix"),
36+
value: hostPrefix)
37+
}
38+
return next.handle(context: copiedContext, input: input)
39+
}
40+
41+
public typealias MInput = OperationStackInput
42+
public typealias MOutput = OperationOutput<OperationStackOutput>
43+
public typealias Context = HttpContext
44+
public typealias MError = SdkError<OperationStackError>
45+
}

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/ClientRuntimeTypes.kt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,8 @@ object ClientRuntimeTypes {
5959
val DeserializeMiddleware = runtimeSymbol("DeserializeMiddleware")
6060
val MutateHeadersMiddleware = runtimeSymbol("MutateHeadersMiddleware")
6161
val OperationStack = runtimeSymbol("OperationStack")
62-
62+
val URLHostMiddleware = runtimeSymbol("URLHostMiddleware")
63+
val SerializableBodyMiddleware = runtimeSymbol("SerializableBodyMiddleware")
6364
val NoopHandler = runtimeSymbol("NoopHandler")
6465
}
6566

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/HttpBindingProtocolGenerator.kt

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,6 @@ import software.amazon.smithy.swift.codegen.integration.middlewares.OperationInp
4949
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.HttpBodyMiddleware
5050
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.HttpHeaderMiddleware
5151
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.HttpQueryItemMiddleware
52-
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.HttpUrlHostMiddleware
5352
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.HttpUrlPathMiddleware
5453
import software.amazon.smithy.swift.codegen.integration.serde.DynamicNodeDecodingGeneratorStrategy
5554
import software.amazon.smithy.swift.codegen.integration.serde.UnionDecodeGeneratorStrategy
@@ -130,11 +129,10 @@ abstract class HttpBindingProtocolGenerator : ProtocolGenerator {
130129
continue
131130
}
132131
val httpBindingResolver = getProtocolHttpBindingResolver(ctx, defaultContentType)
133-
HttpUrlHostMiddleware.renderMiddleware(ctx, operation, httpBindingResolver)
134132
HttpUrlPathMiddleware.renderUrlPathMiddleware(ctx, operation, httpBindingResolver)
135133
HttpHeaderMiddleware.renderHeaderMiddleware(ctx, operation, httpBindingResolver, defaultTimestampFormat)
136134
HttpQueryItemMiddleware.renderQueryMiddleware(ctx, operation, httpBindingResolver, defaultTimestampFormat)
137-
HttpBodyMiddleware.renderBodyMiddleware(ctx, operation, httpBindingResolver, httpProtocolBodyMiddleware())
135+
HttpBodyMiddleware.renderBodyMiddleware(ctx, operation, httpBindingResolver)
138136
inputShapesWithHttpBindings.add(inputShapeId)
139137
}
140138
}
@@ -380,13 +378,12 @@ abstract class HttpBindingProtocolGenerator : ProtocolGenerator {
380378

381379
override fun initializeMiddleware(ctx: ProtocolGenerator.GenerationContext) {
382380
val resolver = getProtocolHttpBindingResolver(ctx, defaultContentType)
383-
384381
for (operation in getHttpBindingOperations(ctx)) {
385382
operationMiddleware.appendMiddleware(operation, IdempotencyTokenMiddleware(ctx.model, ctx.symbolProvider))
386383

387384
operationMiddleware.appendMiddleware(operation, ContentMD5Middleware(ctx.model, ctx.symbolProvider))
388385
operationMiddleware.appendMiddleware(operation, OperationInputUrlPathMiddleware(ctx.model, ctx.symbolProvider, ""))
389-
operationMiddleware.appendMiddleware(operation, OperationInputUrlHostMiddleware(ctx.model, ctx.symbolProvider, ""))
386+
operationMiddleware.appendMiddleware(operation, OperationInputUrlHostMiddleware(ctx.model, ctx.symbolProvider, operation))
390387
operationMiddleware.appendMiddleware(operation, OperationInputHeadersMiddleware(ctx.model, ctx.symbolProvider))
391388
operationMiddleware.appendMiddleware(operation, OperationInputQueryItemMiddleware(ctx.model, ctx.symbolProvider))
392389
operationMiddleware.appendMiddleware(operation, ContentTypeMiddleware(ctx.model, ctx.symbolProvider, resolver.determineRequestContentType(operation)))
@@ -430,10 +427,6 @@ abstract class HttpBindingProtocolGenerator : ProtocolGenerator {
430427
)
431428
protected abstract fun addProtocolSpecificMiddleware(ctx: ProtocolGenerator.GenerationContext, operation: OperationShape)
432429

433-
open fun httpProtocolBodyMiddleware(): HttpProtocolBodyMiddlewareGeneratorFactory {
434-
return DefaultHttpProtocolBodyMiddlewareGeneratorFactory()
435-
}
436-
437430
/**
438431
* Get the operations with HTTP Bindings.
439432
*

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/HttpProtocolBodyMiddlewareGeneratorFactory.kt

Lines changed: 0 additions & 37 deletions
This file was deleted.

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/HttpProtocolTestGenerator.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ class HttpProtocolTestGenerator(
8383
val hostMiddlewares = cloned.middlewares(operation, MiddlewareStep.INITIALIZESTEP)
8484
.filter { it.name.contains("HostMiddleware") }
8585
if (hostMiddlewares.isEmpty()) {
86-
cloned.appendMiddleware(operation, OperationInputUrlHostMiddleware(ctx.model, ctx.symbolProvider, "host: hostOnly"))
86+
cloned.appendMiddleware(operation, OperationInputUrlHostMiddleware(ctx.model, ctx.symbolProvider, operation, true))
8787
}
8888
}
8989
return cloned

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/middlewares/OperationInputBodyMiddleware.kt

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package software.amazon.smithy.swift.codegen.integration.middlewares
33
import software.amazon.smithy.codegen.core.SymbolProvider
44
import software.amazon.smithy.model.Model
55
import software.amazon.smithy.model.shapes.OperationShape
6+
import software.amazon.smithy.swift.codegen.ClientRuntimeTypes
67
import software.amazon.smithy.swift.codegen.SwiftWriter
78
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.MiddlewareShapeUtils
89
import software.amazon.smithy.swift.codegen.middleware.MiddlewarePosition
@@ -12,7 +13,7 @@ import software.amazon.smithy.swift.codegen.middleware.MiddlewareStep
1213
class OperationInputBodyMiddleware(
1314
val model: Model,
1415
val symbolProvider: SymbolProvider,
15-
val shouldRender: Boolean = false
16+
val alwaysSendBody: Boolean = false
1617
) : MiddlewareRenderable {
1718

1819
override val name = "OperationInputBodyMiddleware"
@@ -27,9 +28,16 @@ class OperationInputBodyMiddleware(
2728
operationStackName: String,
2829
) {
2930
val inputShapeName = MiddlewareShapeUtils.inputSymbol(symbolProvider, model, op).name
30-
val hasHttpBody = MiddlewareShapeUtils.hasHttpBody(model, op)
31-
if (hasHttpBody || shouldRender) {
32-
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}BodyMiddleware())")
31+
val outputShapeName = MiddlewareShapeUtils.outputSymbol(symbolProvider, model, op).name
32+
val errorShapeName = MiddlewareShapeUtils.outputErrorSymbolName(op)
33+
if (alwaysSendBody) {
34+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: \$N<$inputShapeName, $outputShapeName, $errorShapeName>(alwaysSendBody: true))", ClientRuntimeTypes.Middleware.SerializableBodyMiddleware)
35+
} else if (MiddlewareShapeUtils.hasHttpBody(model, op)) {
36+
if (MiddlewareShapeUtils.bodyIsHttpPayload(model, op)) {
37+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}BodyMiddleware())")
38+
} else {
39+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: \$N<$inputShapeName, $outputShapeName, $errorShapeName>())", ClientRuntimeTypes.Middleware.SerializableBodyMiddleware)
40+
}
3341
}
3442
}
3543
}

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/middlewares/OperationInputHeadersMiddleware.kt

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ import software.amazon.smithy.swift.codegen.middleware.MiddlewareStep
1111

1212
class OperationInputHeadersMiddleware(
1313
val model: Model,
14-
val symbolProvider: SymbolProvider,
14+
val symbolProvider: SymbolProvider
1515
) : MiddlewareRenderable {
1616

1717
override val name = "OperationInputHeadersMiddleware"
@@ -26,6 +26,9 @@ class OperationInputHeadersMiddleware(
2626
operationStackName: String,
2727
) {
2828
val inputShapeName = MiddlewareShapeUtils.inputSymbol(symbolProvider, model, op).name
29-
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}HeadersMiddleware())")
29+
val hasHeaders = MiddlewareShapeUtils.hasHttpHeaders(model, op)
30+
if (hasHeaders) {
31+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}HeadersMiddleware())")
32+
}
3033
}
3134
}

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/middlewares/OperationInputQueryItemMiddleware.kt

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,9 @@ class OperationInputQueryItemMiddleware(
2626
operationStackName: String,
2727
) {
2828
val inputShapeName = MiddlewareShapeUtils.inputSymbol(symbolProvider, model, op).name
29-
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}QueryItemMiddleware())")
29+
val hasQueryItems = MiddlewareShapeUtils.hasQueryItems(model, op)
30+
if (hasQueryItems) {
31+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}QueryItemMiddleware())")
32+
}
3033
}
3134
}

smithy-swift-codegen/src/main/kotlin/software/amazon/smithy/swift/codegen/integration/middlewares/OperationInputUrlHostMiddleware.kt

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,16 +3,21 @@ package software.amazon.smithy.swift.codegen.integration.middlewares
33
import software.amazon.smithy.codegen.core.SymbolProvider
44
import software.amazon.smithy.model.Model
55
import software.amazon.smithy.model.shapes.OperationShape
6+
import software.amazon.smithy.model.traits.EndpointTrait
7+
import software.amazon.smithy.swift.codegen.ClientRuntimeTypes
68
import software.amazon.smithy.swift.codegen.SwiftWriter
9+
import software.amazon.smithy.swift.codegen.integration.EndpointTraitConstructor
710
import software.amazon.smithy.swift.codegen.integration.middlewares.handlers.MiddlewareShapeUtils
811
import software.amazon.smithy.swift.codegen.middleware.MiddlewarePosition
912
import software.amazon.smithy.swift.codegen.middleware.MiddlewareRenderable
1013
import software.amazon.smithy.swift.codegen.middleware.MiddlewareStep
14+
import software.amazon.smithy.swift.codegen.model.getTrait
1115

1216
class OperationInputUrlHostMiddleware(
1317
val model: Model,
1418
val symbolProvider: SymbolProvider,
15-
val inputParameters: String
19+
val operation: OperationShape,
20+
val requiresHost: Boolean = false
1621
) : MiddlewareRenderable {
1722

1823
override val name = "OperationInputUrlHostMiddleware"
@@ -27,6 +32,16 @@ class OperationInputUrlHostMiddleware(
2732
operationStackName: String
2833
) {
2934
val inputShapeName = MiddlewareShapeUtils.inputSymbol(symbolProvider, model, op).name
30-
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: ${inputShapeName}URLHostMiddleware($inputParameters))")
35+
val outputShapeName = MiddlewareShapeUtils.outputSymbol(symbolProvider, model, op).name
36+
val errorShapeName = MiddlewareShapeUtils.outputErrorSymbolName(op)
37+
38+
var inputParameters = if (requiresHost) "host: hostOnly" else ""
39+
operation.getTrait<EndpointTrait>()?.let {
40+
val inputShape = model.expectShape(operation.input.get())
41+
val hostPrefix = EndpointTraitConstructor(it, inputShape).construct()
42+
inputParameters += if (requiresHost) ", " else ""
43+
inputParameters += "hostPrefix: \"$hostPrefix\""
44+
}
45+
writer.write("$operationStackName.${middlewareStep.stringValue()}.intercept(position: ${position.stringValue()}, middleware: \$N<$inputShapeName, $outputShapeName, $errorShapeName>($inputParameters))", ClientRuntimeTypes.Middleware.URLHostMiddleware)
3146
}
3247
}

0 commit comments

Comments
 (0)