8#include <userver/compiler/select.hpp>
9#include <userver/utils/any_movable.hpp>
10#include <userver/utils/fast_pimpl.hpp>
12USERVER_NAMESPACE_BEGIN
20class RequestContext
final {
24 RequestContext(RequestContext&&)
noexcept;
26 RequestContext(
const RequestContext&) =
delete;
32 template <
typename Data>
37 template <
typename Data,
typename... Args>
43 template <
typename Data>
49 template <
typename Data>
54 template <
typename Data>
59 template <
typename Data>
68 template <
typename Data>
69 Data&
SetData(std::string name, Data data);
74 template <
typename Data,
typename... Args>
75 Data&
EmplaceData(std::string name, Args&&... args);
80 template <
typename Data>
81 Data&
GetData(
const std::string& name);
86 template <
typename Data>
87 const Data&
GetData(
const std::string& name)
const;
91 template <
typename Data>
96 template <
typename Data>
106 static constexpr std::size_t kPimplSize = compiler::SelectSize()
112 utils::AnyMovable& SetUserAnyData(
utils::AnyMovable&& data);
113 utils::AnyMovable& GetUserAnyData();
114 utils::AnyMovable* GetUserAnyDataOptional();
115 void EraseUserAnyData();
117 utils::AnyMovable& SetAnyData(std::string&& name,
utils::AnyMovable&& data);
118 utils::AnyMovable& GetAnyData(
const std::string& name);
119 utils::AnyMovable* GetAnyDataOptional(
const std::string& name);
120 void EraseAnyData(
const std::string& name);
122 utils::FastPimpl<Impl, kPimplSize,
alignof(
void*), utils::kStrictMatch> impl_;
125template <
typename Data>
127 return utils::AnyCast<Data&>(SetUserAnyData(std::move(data)));
130template <
typename Data,
typename... Args>
132 return utils::AnyCast<Data&>(
133 SetUserAnyData(Data(std::forward<Args>(args)...)));
136template <
typename Data>
138 return utils::AnyCast<Data&>(GetUserAnyData());
141template <
typename Data>
144 return const_cast<RequestContext*>(
this)->GetUserData<Data>();
147template <
typename Data>
149 auto* data = GetUserAnyDataOptional();
150 return data ? &
utils::AnyCast<Data&>(*data) :
nullptr;
153template <
typename Data>
157 return const_cast<RequestContext*>(
this)->GetUserDataOptional<Data>();
162template <
typename Data>
163Data& RequestContext::
SetData(std::string name, Data data) {
164 return utils::AnyCast<Data&>(SetAnyData(std::move(name), std::move(data)));
167template <
typename Data,
typename... Args>
168Data& RequestContext::
EmplaceData(std::string name, Args&&... args) {
169 return utils::AnyCast<Data&>(
170 SetAnyData(std::move(name), Data(std::forward<Args>(args)...)));
173template <
typename Data>
174Data& RequestContext::
GetData(
const std::string& name) {
175 return utils::AnyCast<Data&>(GetAnyData(name));
178template <
typename Data>
179const Data& RequestContext::
GetData(
const std::string& name)
const {
181 return const_cast<RequestContext*>(
this)->GetData<Data>(name);
184template <
typename Data>
187 auto* data = GetAnyDataOptional(name);
188 return data ? &
utils::AnyCast<Data&>(*data) :
nullptr;
191template <
typename Data>
195 return const_cast<RequestContext*>(
this)->GetDataOptional<Data>(name);
198inline void RequestContext::
EraseData(
const std::string& name) {