diff --git a/actix-service/CHANGES.md b/actix-service/CHANGES.md
index ca18613d..0c85bd13 100644
--- a/actix-service/CHANGES.md
+++ b/actix-service/CHANGES.md
@@ -4,6 +4,9 @@
 
 ### Add missing Clone impls
 
+### Restore `Transform::map_init_err()` combinator
+
+
 ## [1.0.0-alpha.2] - 2019-12-02
 
 ### Use owned config value for service factory
diff --git a/actix-service/src/and_then.rs b/actix-service/src/and_then.rs
index 6f631b96..14bfcac7 100644
--- a/actix-service/src/and_then.rs
+++ b/actix-service/src/and_then.rs
@@ -126,7 +126,13 @@ where
 pub struct AndThenServiceFactory<A, B>
 where
     A: ServiceFactory,
-    B: ServiceFactory,
+    A::Config: Clone,
+    B: ServiceFactory<
+        Config = A::Config,
+        Request = A::Response,
+        Error = A::Error,
+        InitError = A::InitError,
+    >,
 {
     a: A,
     b: B,
@@ -180,7 +186,13 @@ where
 impl<A, B> Clone for AndThenServiceFactory<A, B>
 where
     A: ServiceFactory + Clone,
-    B: ServiceFactory + Clone,
+    A::Config: Clone,
+    B: ServiceFactory<
+            Config = A::Config,
+            Request = A::Response,
+            Error = A::Error,
+            InitError = A::InitError,
+        > + Clone,
 {
     fn clone(&self) -> Self {
         Self {
diff --git a/actix-service/src/apply.rs b/actix-service/src/apply.rs
index 5fb984d4..ae498160 100644
--- a/actix-service/src/apply.rs
+++ b/actix-service/src/apply.rs
@@ -80,6 +80,8 @@ where
 pub struct ApplyServiceFactory<T, F, R, In, Out, Err>
 where
     T: ServiceFactory<Error = Err>,
+    F: FnMut(In, &mut T::Service) -> R + Clone,
+    R: Future<Output = Result<Out, Err>>,
 {
     service: T,
     f: F,
diff --git a/actix-service/src/lib.rs b/actix-service/src/lib.rs
index d3138d62..f0cd60e3 100644
--- a/actix-service/src/lib.rs
+++ b/actix-service/src/lib.rs
@@ -23,6 +23,7 @@ mod map_init_err;
 mod pipeline;
 mod then;
 mod transform;
+mod transform_err;
 
 pub use self::apply::{apply_fn, apply_fn_factory};
 pub use self::apply_cfg::{apply_cfg, apply_cfg_factory};
@@ -323,4 +324,5 @@ pub mod dev {
     pub use crate::map_init_err::MapInitErr;
     pub use crate::then::{ThenService, ThenServiceFactory};
     pub use crate::transform::ApplyTransform;
+    pub use crate::transform_err::TransformMapInitErr;
 }
diff --git a/actix-service/src/transform.rs b/actix-service/src/transform.rs
index f1e4ee41..08d325d1 100644
--- a/actix-service/src/transform.rs
+++ b/actix-service/src/transform.rs
@@ -4,6 +4,7 @@ use std::rc::Rc;
 use std::sync::Arc;
 use std::task::{Context, Poll};
 
+use crate::transform_err::TransformMapInitErr;
 use crate::{IntoServiceFactory, Service, ServiceFactory};
 
 /// Apply transform to a service. Function returns
@@ -48,6 +49,16 @@ pub trait Transform<S> {
 
     /// Creates and returns a new Service component, asynchronously
     fn new_transform(&self, service: S) -> Self::Future;
+
+    /// Map this transforms's factory error to a different error,
+    /// returning a new transform service factory.
+    fn map_init_err<F, E>(self, f: F) -> TransformMapInitErr<Self, S, F, E>
+    where
+        Self: Sized,
+        F: Fn(Self::InitError) -> E + Clone,
+    {
+        TransformMapInitErr::new(self, f)
+    }
 }
 
 impl<T, S> Transform<S> for Rc<T>
diff --git a/actix-service/src/transform_err.rs b/actix-service/src/transform_err.rs
new file mode 100644
index 00000000..c3a71ab6
--- /dev/null
+++ b/actix-service/src/transform_err.rs
@@ -0,0 +1,94 @@
+use std::future::Future;
+use std::marker::PhantomData;
+use std::pin::Pin;
+use std::task::{Context, Poll};
+
+use super::Transform;
+
+/// Transform for the `map_init_err` combinator, changing the type of a new
+/// transform's init error.
+///
+/// This is created by the `Transform::map_init_err` method.
+pub struct TransformMapInitErr<T, S, F, E> {
+    t: T,
+    f: F,
+    e: PhantomData<(S, E)>,
+}
+
+impl<T, S, F, E> TransformMapInitErr<T, S, F, E> {
+    pub(crate) fn new(t: T, f: F) -> Self
+    where
+        T: Transform<S>,
+        F: Fn(T::InitError) -> E,
+    {
+        Self {
+            t,
+            f,
+            e: PhantomData,
+        }
+    }
+}
+
+impl<T, S, F, E> Clone for TransformMapInitErr<T, S, F, E>
+where
+    T: Clone,
+    F: Clone,
+{
+    fn clone(&self) -> Self {
+        Self {
+            t: self.t.clone(),
+            f: self.f.clone(),
+            e: PhantomData,
+        }
+    }
+}
+
+impl<T, S, F, E> Transform<S> for TransformMapInitErr<T, S, F, E>
+where
+    T: Transform<S>,
+    F: Fn(T::InitError) -> E + Clone,
+{
+    type Request = T::Request;
+    type Response = T::Response;
+    type Error = T::Error;
+    type Transform = T::Transform;
+
+    type InitError = E;
+    type Future = TransformMapInitErrFuture<T, S, F, E>;
+
+    fn new_transform(&self, service: S) -> Self::Future {
+        TransformMapInitErrFuture {
+            fut: self.t.new_transform(service),
+            f: self.f.clone(),
+        }
+    }
+}
+
+pin_project! {
+    pub struct TransformMapInitErrFuture<T, S, F, E>
+    where
+        T: Transform<S>,
+        F: Fn(T::InitError) -> E,
+    {
+        #[pin]
+        fut: T::Future,
+        f: F,
+    }
+}
+
+impl<T, S, F, E> Future for TransformMapInitErrFuture<T, S, F, E>
+where
+    T: Transform<S>,
+    F: Fn(T::InitError) -> E + Clone,
+{
+    type Output = Result<T::Transform, E>;
+
+    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
+        let this = self.project();
+        if let Poll::Ready(res) = this.fut.poll(cx) {
+            Poll::Ready(res.map_err(this.f))
+        } else {
+            Poll::Pending
+        }
+    }
+}