1package http
2
3import (
4 "context"
5 "fmt"
6 "net/http/httputil"
7
8 "github.com/aws/smithy-go/logging"
9 "github.com/aws/smithy-go/middleware"
10)
11
12// RequestResponseLogger is a deserialize middleware that will log the request and response HTTP messages and optionally
13// their respective bodies. Will not perform any logging if none of the options are set.
14type RequestResponseLogger struct {
15 LogRequest bool
16 LogRequestWithBody bool
17
18 LogResponse bool
19 LogResponseWithBody bool
20}
21
22// ID is the middleware identifier.
23func (r *RequestResponseLogger) ID() string {
24 return "RequestResponseLogger"
25}
26
27// HandleDeserialize will log the request and response HTTP messages if configured accordingly.
28func (r *RequestResponseLogger) HandleDeserialize(
29 ctx context.Context, in middleware.DeserializeInput, next middleware.DeserializeHandler,
30) (
31 out middleware.DeserializeOutput, metadata middleware.Metadata, err error,
32) {
33 logger := middleware.GetLogger(ctx)
34
35 if r.LogRequest || r.LogRequestWithBody {
36 smithyRequest, ok := in.Request.(*Request)
37 if !ok {
38 return out, metadata, fmt.Errorf("unknown transport type %T", in)
39 }
40
41 rc := smithyRequest.Build(ctx)
42 reqBytes, err := httputil.DumpRequestOut(rc, r.LogRequestWithBody)
43 if err != nil {
44 return out, metadata, err
45 }
46
47 logger.Logf(logging.Debug, "Request\n%v", string(reqBytes))
48
49 if r.LogRequestWithBody {
50 smithyRequest, err = smithyRequest.SetStream(rc.Body)
51 if err != nil {
52 return out, metadata, err
53 }
54 in.Request = smithyRequest
55 }
56 }
57
58 out, metadata, err = next.HandleDeserialize(ctx, in)
59
60 if (err == nil) && (r.LogResponse || r.LogResponseWithBody) {
61 smithyResponse, ok := out.RawResponse.(*Response)
62 if !ok {
63 return out, metadata, fmt.Errorf("unknown transport type %T", out.RawResponse)
64 }
65
66 respBytes, err := httputil.DumpResponse(smithyResponse.Response, r.LogResponseWithBody)
67 if err != nil {
68 return out, metadata, fmt.Errorf("failed to dump response %w", err)
69 }
70
71 logger.Logf(logging.Debug, "Response\n%v", string(respBytes))
72 }
73
74 return out, metadata, err
75}