Skip to content

Commit 8f29948

Browse files
committed
feat: add auto Connection::into_owned
1 parent de96999 commit 8f29948

File tree

1 file changed

+72
-4
lines changed

1 file changed

+72
-4
lines changed

src/server/conn/auto.rs

+72-4
Original file line numberDiff line numberDiff line change
@@ -152,7 +152,7 @@ impl<E> Builder<E> {
152152
#[cfg(any(feature = "http1", feature = "http2"))]
153153
_ => ConnState::ReadVersion {
154154
read_version: read_version(io),
155-
builder: self,
155+
builder: Cow::Borrowed(self),
156156
service: Some(service),
157157
},
158158
};
@@ -180,7 +180,7 @@ impl<E> Builder<E> {
180180
UpgradeableConnection {
181181
state: UpgradeableConnState::ReadVersion {
182182
read_version: read_version(io),
183-
builder: self,
183+
builder: Cow::Borrowed(self),
184184
service: Some(service),
185185
},
186186
}
@@ -292,6 +292,22 @@ pin_project! {
292292
}
293293
}
294294

295+
// A custom COW, since the libstd is has ToOwned bounds that are too eager.
296+
enum Cow<'a, T> {
297+
Borrowed(&'a T),
298+
Owned(T),
299+
}
300+
301+
impl<'a, T> std::ops::Deref for Cow<'a, T> {
302+
type Target = T;
303+
fn deref(&self) -> &T {
304+
match self {
305+
Cow::Borrowed(t) => &*t,
306+
Cow::Owned(ref t) => t,
307+
}
308+
}
309+
}
310+
295311
#[cfg(feature = "http1")]
296312
type Http1Connection<I, S> = hyper::server::conn::http1::Connection<Rewind<I>, S>;
297313

@@ -313,7 +329,7 @@ pin_project! {
313329
ReadVersion {
314330
#[pin]
315331
read_version: ReadVersion<I>,
316-
builder: &'a Builder<E>,
332+
builder: Cow<'a, Builder<E>>,
317333
service: Option<S>,
318334
},
319335
H1 {
@@ -355,6 +371,32 @@ where
355371
_ => unreachable!(),
356372
}
357373
}
374+
375+
/// Make this Connection static, instead of borrowing from Builder.
376+
pub fn into_owned(self) -> Connection<'static, I, S, E>
377+
where
378+
Builder<E>: Clone,
379+
{
380+
Connection {
381+
state: match self.state {
382+
ConnState::ReadVersion {
383+
read_version,
384+
builder,
385+
service,
386+
} => ConnState::ReadVersion {
387+
read_version,
388+
service,
389+
builder: Cow::Owned(builder.clone()),
390+
},
391+
#[cfg(feature = "http1")]
392+
ConnState::H1 { conn } => ConnState::H1 { conn },
393+
#[cfg(feature = "http2")]
394+
ConnState::H2 { conn } => ConnState::H2 { conn },
395+
#[cfg(any(not(feature = "http1"), not(feature = "http2")))]
396+
_ => unreachable!(),
397+
},
398+
}
399+
}
358400
}
359401

360402
impl<I, S, E, B> Future for Connection<'_, I, S, E>
@@ -437,7 +479,7 @@ pin_project! {
437479
ReadVersion {
438480
#[pin]
439481
read_version: ReadVersion<I>,
440-
builder: &'a Builder<E>,
482+
builder: Cow<'a, Builder<E>>,
441483
service: Option<S>,
442484
},
443485
H1 {
@@ -479,6 +521,32 @@ where
479521
_ => unreachable!(),
480522
}
481523
}
524+
525+
/// Make this Connection static, instead of borrowing from Builder.
526+
pub fn into_owned(self) -> UpgradeableConnection<'static, I, S, E>
527+
where
528+
Builder<E>: Clone,
529+
{
530+
UpgradeableConnection {
531+
state: match self.state {
532+
UpgradeableConnState::ReadVersion {
533+
read_version,
534+
builder,
535+
service,
536+
} => UpgradeableConnState::ReadVersion {
537+
read_version,
538+
service,
539+
builder: Cow::Owned(builder.clone()),
540+
},
541+
#[cfg(feature = "http1")]
542+
UpgradeableConnState::H1 { conn } => UpgradeableConnState::H1 { conn },
543+
#[cfg(feature = "http2")]
544+
UpgradeableConnState::H2 { conn } => UpgradeableConnState::H2 { conn },
545+
#[cfg(any(not(feature = "http1"), not(feature = "http2")))]
546+
_ => unreachable!(),
547+
},
548+
}
549+
}
482550
}
483551

484552
impl<I, S, E, B> Future for UpgradeableConnection<'_, I, S, E>

0 commit comments

Comments
 (0)