1- use futures:: { ready, Stream , TryFuture } ;
1+ use futures:: { ready, Stream , TryFuture , TryStream } ;
22use indexmap:: IndexSet ;
3- use linkerd2_proxy_core:: resolve:: { Resolution , Resolve , Update } ;
3+ use linkerd2_proxy_core:: resolve:: { Resolve , Update } ;
44use pin_project:: pin_project;
55use std:: collections:: VecDeque ;
66use std:: future:: Future ;
@@ -10,45 +10,50 @@ use std::task::{Context, Poll};
1010use tower:: discover:: Change ;
1111
1212#[ derive( Clone , Debug ) ]
13- pub struct FromResolve < R > {
13+ pub struct FromResolve < R , E > {
1414 resolve : R ,
15+ _marker : std:: marker:: PhantomData < fn ( E ) > ,
1516}
1617
1718#[ pin_project]
1819#[ derive( Debug ) ]
19- pub struct DiscoverFuture < F > {
20+ pub struct DiscoverFuture < F , E > {
2021 #[ pin]
2122 future : F ,
23+ _marker : std:: marker:: PhantomData < fn ( E ) > ,
2224}
2325
2426/// Observes an `R`-typed resolution stream, using an `M`-typed endpoint stack to
2527/// build a service for each endpoint.
2628#[ pin_project]
27- pub struct Discover < R : Resolution > {
29+ pub struct Discover < R : TryStream , E > {
2830 #[ pin]
2931 resolution : R ,
3032 active : IndexSet < SocketAddr > ,
31- pending : VecDeque < Change < SocketAddr , R :: Endpoint > > ,
33+ pending : VecDeque < Change < SocketAddr , E > > ,
3234}
3335
3436// === impl FromResolve ===
3537
36- impl < R > FromResolve < R > {
38+ impl < R , E > FromResolve < R , E > {
3739 pub fn new < T > ( resolve : R ) -> Self
3840 where
3941 R : Resolve < T > ,
4042 {
41- Self { resolve }
43+ Self {
44+ resolve,
45+ _marker : std:: marker:: PhantomData ,
46+ }
4247 }
4348}
4449
45- impl < T , R > tower:: Service < T > for FromResolve < R >
50+ impl < T , R , E > tower:: Service < T > for FromResolve < R , E >
4651where
4752 R : Resolve < T > + Clone ,
4853{
49- type Response = Discover < R :: Resolution > ;
54+ type Response = Discover < R :: Resolution , E > ;
5055 type Error = R :: Error ;
51- type Future = DiscoverFuture < R :: Future > ;
56+ type Future = DiscoverFuture < R :: Future , E > ;
5257
5358 #[ inline]
5459 fn poll_ready ( & mut self , cx : & mut Context < ' _ > ) -> Poll < Result < ( ) , Self :: Error > > {
@@ -59,18 +64,19 @@ where
5964 fn call ( & mut self , target : T ) -> Self :: Future {
6065 Self :: Future {
6166 future : self . resolve . resolve ( target) ,
67+ _marker : std:: marker:: PhantomData ,
6268 }
6369 }
6470}
6571
6672// === impl DiscoverFuture ===
6773
68- impl < F > Future for DiscoverFuture < F >
74+ impl < F , E > Future for DiscoverFuture < F , E >
6975where
7076 F : TryFuture ,
71- F :: Ok : Resolution ,
77+ F :: Ok : TryStream ,
7278{
73- type Output = Result < Discover < F :: Ok > , F :: Error > ;
79+ type Output = Result < Discover < F :: Ok , E > , F :: Error > ;
7480
7581 fn poll ( self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < Self :: Output > {
7682 let resolution = ready ! ( self . project( ) . future. try_poll( cx) ) ?;
8086
8187// === impl Discover ===
8288
83- impl < R : Resolution > Discover < R > {
89+ impl < R : TryStream , E > Discover < R , E > {
8490 pub fn new ( resolution : R ) -> Self {
8591 Self {
8692 resolution,
@@ -90,8 +96,11 @@ impl<R: Resolution> Discover<R> {
9096 }
9197}
9298
93- impl < R : Resolution > Stream for Discover < R > {
94- type Item = Result < Change < SocketAddr , R :: Endpoint > , R :: Error > ;
99+ impl < R , E > Stream for Discover < R , E >
100+ where
101+ R : TryStream < Ok = Update < E > > ,
102+ {
103+ type Item = Result < Change < SocketAddr , E > , R :: Error > ;
95104
96105 fn poll_next ( mut self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < Option < Self :: Item > > {
97106 loop {
@@ -100,24 +109,27 @@ impl<R: Resolution> Stream for Discover<R> {
100109 return Poll :: Ready ( Some ( Ok ( change) ) ) ;
101110 }
102111
103- match ready ! ( this. resolution. poll( cx) ) ? {
104- Update :: Add ( endpoints) => {
105- for ( addr, endpoint) in endpoints. into_iter ( ) {
106- this. active . insert ( addr) ;
107- this. pending . push_back ( Change :: Insert ( addr, endpoint) ) ;
112+ match ready ! ( this. resolution. try_poll_next( cx) ) {
113+ Some ( update) => match update? {
114+ Update :: Add ( endpoints) => {
115+ for ( addr, endpoint) in endpoints. into_iter ( ) {
116+ this. active . insert ( addr) ;
117+ this. pending . push_back ( Change :: Insert ( addr, endpoint) ) ;
118+ }
108119 }
109- }
110- Update :: Remove ( addrs) => {
111- for addr in addrs . into_iter ( ) {
112- if this. active . remove ( & addr) {
113- this . pending . push_back ( Change :: Remove ( addr ) ) ;
120+ Update :: Remove ( addrs ) => {
121+ for addr in addrs. into_iter ( ) {
122+ if this . active . remove ( & addr ) {
123+ this. pending . push_back ( Change :: Remove ( addr) ) ;
124+ }
114125 }
115126 }
116- }
117- Update :: DoesNotExist | Update :: Empty => {
118- this. pending
119- . extend ( this. active . drain ( ..) . map ( Change :: Remove ) ) ;
120- }
127+ Update :: DoesNotExist | Update :: Empty => {
128+ this. pending
129+ . extend ( this. active . drain ( ..) . map ( Change :: Remove ) ) ;
130+ }
131+ } ,
132+ None => return Poll :: Ready ( None ) ,
121133 }
122134 }
123135 }
0 commit comments