@@ -172,3 +172,56 @@ where
172172 }
173173 }
174174}
175+
176+ #[ cfg( test) ]
177+ mod test_stream_adapter {
178+ use super :: * ;
179+
180+ use crate :: Body ;
181+ use http:: StatusCode ;
182+
183+ // A middleware that logs requests before forwarding them to another service
184+ struct LogService < S > {
185+ inner : S ,
186+ }
187+
188+ impl < S > Service < LambdaEvent < LambdaRequest > > for LogService < S >
189+ where
190+ S : Service < LambdaEvent < LambdaRequest > > ,
191+ {
192+ type Response = S :: Response ;
193+ type Error = S :: Error ;
194+ type Future = S :: Future ;
195+
196+ fn poll_ready ( & mut self , cx : & mut Context < ' _ > ) -> Poll < Result < ( ) , Self :: Error > > {
197+ self . inner . poll_ready ( cx)
198+ }
199+
200+ fn call ( & mut self , event : LambdaEvent < LambdaRequest > ) -> Self :: Future {
201+ // Log the request
202+ println ! ( "Lambda event: {event:#?}" ) ;
203+
204+ self . inner . call ( event)
205+ }
206+ }
207+
208+ /// This tests that `StreamAdapter` can be used in a `tower::Service` where
209+ /// the user may require additional middleware between `lambda_runtime::run`
210+ /// and where the `LambdaEvent` is converted into a `Request`.
211+ #[ test]
212+ fn stream_adapter_is_boxable ( ) {
213+ let _svc = ServiceBuilder :: new ( )
214+ . layer_fn ( |service| {
215+ // This could be any middleware that logs, inspects, or
216+ // manipulates the `LambdaEvent` before it's converted to a
217+ // `Request` by `Adapter`.
218+
219+ LogService { inner : service }
220+ } )
221+ . layer_fn ( StreamAdapter :: from)
222+ . service_fn (
223+ |_req : Request | async move { http:: Response :: builder ( ) . status ( StatusCode :: OK ) . body ( Body :: Empty ) } ,
224+ )
225+ . boxed ( ) ;
226+ }
227+ }
0 commit comments