capydi
Loading...
Searching...
No Matches
Tag.hpp
Go to the documentation of this file.
1#ifndef TAG_CONFIG_HPP_
2#define TAG_CONFIG_HPP_
3
9#include "capydi/Error.hpp"
10
14#include <tuple>
15#include <expected>
16#include <optional>
17#include <algorithm>
18
19namespace capy::di
20{
21
23{
24
25template<
26 CreationalConfig Decoratee,
27 typename TagComparator
28>
30 : public DecoratableConfig<
31 TagFilter<Decoratee, TagComparator>
32 >
33{
34public:
35 constexpr explicit TagFilter(TagComparator&& comparator, Decoratee&& decoratee)
36 : decoratee_ { std::move(decoratee) }
37 , comparator_ { std::move(comparator) }
38 {}
39
40public:
42 using /* meta::Pack<meta::Pack<?>> */ ResolutionKeysPack = resolution_keys_pack_t<Decoratee>;
44
45public:
47
48public:
49 template<typename Key>
50 std::expected<meta::RuntimeRef<Key>, Error> do_resolve(
51 meta::Pack<Key>&& keys,
52 auto& dependencies,
54 const auto& input
55 ) const
56 {
57 std::optional<TagInput> tag_input = input.template retrieve_override<TagInput>();
58
59 if (!tag_input.has_value()) [[unlikely]]
60 {
61 return std::unexpected { Error::TAG_CONFIG_EXPECTED };
62 }
63
64 const tag_t input_tag = tag_input.value().tag.value();
65
66 if (!this->comparator_(input_tag)) [[unlikely]]
67 {
68 return std::unexpected { Error::TAG_MISMATCH };
69 }
70
71 return decoratee_.do_resolve(
72 keys,
73 dependencies,
74 context,
75 input
76 );
77 }
78
79 template<std::size_t DependencyIndex>
81 {
82 return this->decoratee_
84 }
85
86private:
87 Decoratee decoratee_;
88 TagComparator comparator_;
89};
90
91template<
92 ChainableConfig Decoratee,
93 typename TagComparator
94>
96 : public DecoratableConfig<
97 TagFilterChainable<Decoratee, TagComparator>
98 >
99{
100public:
101 constexpr explicit TagFilterChainable(
102 TagComparator&& comparator,
103 Decoratee&& decoratee
104 )
105 : decoratee_ { std::move(decoratee) }
106 , comparator_ { std::move(comparator) }
107 {}
108
109public:
112
113public:
115
116public:
119 meta::Reference<RelatedEntity> auto decoratee,
121 ) const
122 {
123 using InputsPack = meta::rebind_t<
124 decltype(context.input),
125 std::tuple,
127 >;
128 using ResultType = decltype(this->decoratee_.pipe(decoratee, context));
129
131 {
132 const TagInput& tag_input = std::get<TagInput>(context.input);
133
134 if (!this->comparator_(tag_input.tag.value()))
135 {
136 return ResultType {
137 decoratee
138 };
139 }
140
141 return this->decoratee_.pipe(decoratee, context);
142 }
143 else
144 {
145 return ResultType {
146 decoratee
147 };
148 }
149 }
150
151
152private:
153 Decoratee decoratee_;
154 TagComparator comparator_;
155};
156
157}
158
159struct Tag
160{
161 template<CreationalConfig Decoratee>
162 static constexpr auto decorate(
163 Decoratee&& decoratee,
164 tag_t tag
165 ) {
167 [tag](const tag_t& inner_tag) { return inner_tag == tag; },
168 std::forward<Decoratee>(decoratee)
169 };
170 }
171
172 template<ChainableConfig Decoratee>
173 static constexpr auto decorate_chainable(
174 Decoratee&& decoratee,
175 tag_t tag
176 ) {
178 [tag](const tag_t& inner_tag) { return inner_tag == tag; },
179 std::forward<Decoratee>(decoratee)
180 };
181 }
182};
183
185{
186 template<
187 CreationalConfig Decoratee,
188 typename TagComparator
189 >
192 Decoratee&& decoratee,
193 TagComparator&& tag_comparator
194 )
195 {
197 std::move(tag_comparator),
198 std::forward<Decoratee>(decoratee)
199 };
200 }
201
202 template<
203 ChainableConfig Decoratee,
204 typename TagComparator
205 >
208 Decoratee&& decoratee,
209 TagComparator&& tag_comparator
210 )
211 {
213 std::move(tag_comparator),
214 std::forward<Decoratee>(decoratee)
215 };
216 }
217};
218
219}
220
221#endif // !TAG_CONFIG_HPP_
Concept and utilities for chainable (decorator/pipeline) configurations.
Concept and utilities for creational (factory/constructor) configurations.
Error codes and diagnostics for dependency injection operations.
Compile-time type pack utilities and metaprogramming foundations.
constexpr Type & value() noexcept
Definition RequiredFieldsUsageValidator.hpp:69
Resolution< RelatedEntity, Error > auto pipe(meta::Reference< RelatedEntity > auto decoratee, meta::wrapped_with< ResolutionContext > auto &context) const
Definition Tag.hpp:118
constexpr TagFilterChainable(TagComparator &&comparator, Decoratee &&decoratee)
Definition Tag.hpp:101
get_related_keys_pack_t< Decoratee > RelatedKeysPack
Definition Tag.hpp:111
static constexpr ConfigType CONFIG_TYPE
Definition Tag.hpp:114
get_related_entity_t< Decoratee > RelatedEntity
Definition Tag.hpp:110
static constexpr ConfigType CONFIG_TYPE
Definition Tag.hpp:46
meta::wrapped_with< std::optional > auto get_dependencies_input() const
Definition Tag.hpp:80
std::expected< meta::RuntimeRef< Key >, Error > do_resolve(meta::Pack< Key > &&keys, auto &dependencies, meta::wrapped_with< ResolutionContext > auto &context, const auto &input) const
Definition Tag.hpp:50
constexpr TagFilter(TagComparator &&comparator, Decoratee &&decoratee)
Definition Tag.hpp:35
central_type_t< Decoratee > CentralType
Definition Tag.hpp:41
dependencies_pack_t< Decoratee > DependenciesPack
Definition Tag.hpp:43
resolution_keys_pack_t< Decoratee > ResolutionKeysPack
Definition Tag.hpp:42
Concept for configuration objects that transform/decorate dependencies.
Definition ChainableConfig.hpp:58
Concept for configurations that handle dependency creation and instantiation.
Definition CreationalConfig.hpp:50
Definition Resolution.hpp:30
Definition Reference.hpp:10
Definition WrappedWIth.hpp:30
Definition DependencyTags.hpp:18
Definition Decorator.hpp:19
const char * tag_t
Definition TagInput.hpp:9
typename Config::RelatedEntity get_related_entity_t
Helper alias to extract the entity type from a ChainableConfig.
Definition ChainableConfig.hpp:92
typename Config::RelatedKeysPack get_related_keys_pack_t
Helper alias to extract the key type from a ChainableConfig.
Definition ChainableConfig.hpp:96
typename Config::DependenciesPack dependencies_pack_t
Definition CreationalConfig.hpp:82
typename Config::ResolutionKeysPack resolution_keys_pack_t
Helper alias to extract the resolution keys from a CreationalConfig.
Definition CreationalConfig.hpp:79
ConfigType
Categorization of configuration strategies in the DI container.
Definition ConfigType.hpp:24
@ CHAINABLE
Chainable configs form a pipeline of transformations applied after creation. Examples: proxies,...
Definition ConfigType.hpp:35
@ CREATIONAL
Creational configs handle object instantiation and factory patterns. These are responsible for creati...
Definition ConfigType.hpp:27
Error
Enumeration of possible errors during dependency injection resolution.
Definition Error.hpp:26
@ TAG_CONFIG_EXPECTED
Definition Error.hpp:39
@ TAG_MISMATCH
Definition Error.hpp:41
typename Config::CentralType central_type_t
Helper alias to extract the central type from a CreationalConfig.
Definition CreationalConfig.hpp:75
typename typed__::Rebind< Type, SrcContainer, DstContainer >::type rebind_t
Definition Rebind.hpp:121
constexpr bool pack_contains_t
Definition Contains.hpp:13
Definition DecoratableConfig.hpp:9
Definition Tag.hpp:185
static constexpr implementation_details_::TagFilter< Decoratee, TagComparator > decorate(Decoratee &&decoratee, TagComparator &&tag_comparator)
Definition Tag.hpp:191
static constexpr implementation_details_::TagFilterChainable< Decoratee, TagComparator > decorate_chainable(Decoratee &&decoratee, TagComparator &&tag_comparator)
Definition Tag.hpp:207
Definition TagInput.hpp:12
RequiredField< tag_t > tag
Definition TagInput.hpp:20
Definition Tag.hpp:160
static constexpr auto decorate_chainable(Decoratee &&decoratee, tag_t tag)
Definition Tag.hpp:173
static constexpr auto decorate(Decoratee &&decoratee, tag_t tag)
Definition Tag.hpp:162
A compile-time heterogeneous type list.
Definition Pack.hpp:70