1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
//! A crate for targeting and accessing _actual implementation_.
//!
//! Take an example trait:
//!
//! ```rust
//! # struct Website;
//! trait ScrapeTheInternet {
//!     fn scrape_the_internet(&self) -> Vec<Website>;
//! }
//! ```
//!
//! The trait represents some abstract computation. The trait exports a method signature that
//! can be implemented by types. In this case, we can imagine what a true implementation of the
//! trait will do: _Actually scrape the internet_.
//!
//! `implementation` provides the [Impl] type as an implementation target for traits having the following semantics:
//!
//! * The trait has only one actual, true implementation.
//! * Other implementations of the trait _may exist_, but these are interpreted as _fake_, _mocked_ in some way.
//!
//! `implementation` enables a standardized way of writing these actual implementations in a way
//! that allows the actual `Self`-receiver type to be unknown.
//!
//! # Usage
//! To define the actual, generic implementation of `ScrapeTheInternet`, we can write the following impl:
//!
//! ```rust
//! # struct Website;
//! # trait ScrapeTheInternet {
//! #    fn scrape_the_internet(&self) -> Vec<Website>;
//! # }
//! impl<T> ScrapeTheInternet for implementation::Impl<T> {
//!     fn scrape_the_internet(&self) -> Vec<Website> {
//!         todo!("find all the web pages, etc")
//!     }
//! }
//! ```
//!
//! This code implements the trait for [Impl], and by doing that we have asserted
//! that it is the actual, true implementation.
//!
//! The implementation is fully generic, and works for any `T`.
//!
//! ```no_run
//! # struct Website;
//! # trait ScrapeTheInternet {
//! #    fn scrape_the_internet(&self) -> Vec<Website>;
//! # }
//! # impl<T> ScrapeTheInternet for implementation::Impl<T> {
//! #     fn scrape_the_internet(&self) -> Vec<Website> {
//! #         todo!("find all the web pages, etc")
//! #     }
//! # }
//! use implementation::Impl;
//!
//! struct MyType;
//!
//! let websites = Impl::new(MyType).scrape_the_internet();
//! ```
//!
//! ## Trait bounds
//! The advantage of keeping trait implementations generic, is that the self type might
//! live in a downstream crate. Let's say we need to access a configuration parameter
//! from `scrape_the_internet`. E.g. the maximum number of pages to scrape:
//!
//! ```rust
//! use implementation::Impl;
//!
//! # struct Website;
//! # trait ScrapeTheInternet {
//! #    fn scrape_the_internet(&self) -> Vec<Website>;
//! # }
//! trait GetMaxNumberOfPages {
//!     fn get_max_number_of_pages(&self) -> Option<usize>;
//! }
//!
//! impl<T> ScrapeTheInternet for Impl<T>
//!     where Impl<T>: GetMaxNumberOfPages
//! {
//!     fn scrape_the_internet(&self) -> Vec<Website> {
//!         let max_number_of_pages = self.get_max_number_of_pages();
//!         todo!("find all the web pages, etc")
//!     }
//! }
//! ```
//!
//! Now, for this to work, `Impl<T>` also needs to implement `GetMaxNumberOfPages` (for the same `T` that is going to be used).
//!
//! `GetMaxNumberOfPages` would likely be implemented for a specific `T` rather than a generic one,
//! since that `T` would typically be some configuration holding that number:
//!
//! ```rust
//! # trait GetMaxNumberOfPages {
//! #     fn get_max_number_of_pages(&self) -> Option<usize>;
//! # }
//! struct Config {
//!     max_number_of_pages: Option<usize>
//! }
//!
//! impl GetMaxNumberOfPages for implementation::Impl<Config> {
//!     fn get_max_number_of_pages(&self) -> Option<usize> {
//!         self.max_number_of_pages
//!     }
//! }
//! ```
//!
//! # Explanation
//!
//! This crate is the solution to a trait coherence problem.
//!
//! Given the trait above, we would like to provide an actual and a mocked implementation.
//! We might know what its actual implementation looks like as an algorithm, but
//! _not what type it should be implemented for_. There could be several reasons
//! to have a generic Self:
//!
//! * The `Self` type might live in a downstream crate
//! * It is actually designed to work generically
//!
//! If we had used a generic Self type (`impl<T> DoSomething for T`), the trait
//! would be unable to also have distinct fake implementations, because that would break
//! the coherence rules: A generic ("blanket") impl and a specialized
//! impl are not allowed to exist at the same time, because that would lead to ambiguity.
//!
//! To solve that, a concrete type is needed as implementation target. But that
//! type is allowed to be generic _internally_. It's just the root level that
//! needs to be a concretely named type.
//!
//! That type is the [Impl] type.
//!
//! When we use this implementation, we can create as many fake implementations as we want.
//!

/// Wrapper type for targeting and accessing actual implementation.
///
/// [Impl] has smart-pointer capabilities, as it implements [std::ops::Deref] and [std::ops::DerefMut].
/// You may freely choose what kind of `T` you want to wrap. It may be an owned one or it could be
/// a `&T`. Each have different tradeoffs.
///
/// An owned `T` is the most flexible in implementations, but that requires always owning "sub-implementations"
/// through an `Impl`:
///
/// ```rust
/// use implementation::Impl;
///
/// struct MyConfig {
///     param1: i32,
///     sub_config: Impl<SubConfig>,
/// }
///
/// struct SubConfig {
///     param2: i32,
/// }
/// ```
///
/// A referenced `&T` makes it possible to _borrow_ an `Impl` from any `T`, but that _could_ prove to be
/// more troublesome in some implementations. This also will require a reference-within-reference
/// design in trait methods with a `&self` receiver, and some more boilerplate if it needs to be cloned:
///
/// ```
/// use implementation::Impl;
///
/// trait DoSomething {
///     fn something(&self);
/// }
///
/// impl<'t, T> DoSomething for Impl<&'t T>
///     where T: Clone + Send + 'static
/// {
///     // self is an `&Impl<&T>`:
///     fn something(&self) {
///
///         // it will require some more code to make a proper clone of T:
///         let t_clone = self.into_inner().clone();
///
///         let handle = std::thread::spawn(move || {
///             let implementation = Impl::new(&t_clone);
///
///             // Do something else with Impl<&T>
///         });
///
///         handle.join().unwrap();
///     }
/// }
/// ```
#[derive(Clone, Copy, Default, Eq, PartialEq, Ord, PartialOrd, Hash, Debug)]
pub struct Impl<T>(T);

impl<T> Impl<T> {
    /// Construct a new [Impl].
    pub fn new(value: T) -> Impl<T> {
        Impl(value)
    }

    pub fn into_inner(self) -> T {
        self.0
    }
}

impl<T> From<T> for Impl<T> {
    fn from(value: T) -> Impl<T> {
        Impl(value)
    }
}

impl<T> std::ops::Deref for Impl<T> {
    type Target = T;

    fn deref(&self) -> &Self::Target {
        &self.0
    }
}

impl<T> std::ops::DerefMut for Impl<T> {
    fn deref_mut(&mut self) -> &mut Self::Target {
        &mut self.0
    }
}

impl<T> AsRef<T> for Impl<T> {
    fn as_ref(&self) -> &T {
        &self.0
    }
}