-
Notifications
You must be signed in to change notification settings - Fork 2
feat: Update provider #121
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
42a776d
e968609
334ec2a
f110e5c
5cc878b
bd66430
5332610
c8fc92d
3f5f4de
b0f3a15
e9e8852
e333df0
c59de28
45ca64a
3b93d77
a4aa1c2
d7cd54a
d6ef2c6
a2f7fee
a91afca
c0482f7
a0ca155
06bd51c
b362223
6942c4e
49bdc17
dab62a0
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,21 @@ | ||
| #ifndef CPP_SDK_INCLUDE_OPENFEATURE_BASE_HOOK_H_ | ||
| #define CPP_SDK_INCLUDE_OPENFEATURE_BASE_HOOK_H_ | ||
|
|
||
| namespace openfeature { | ||
|
|
||
| // Non-templated base class for all hooks. This will allow storing different | ||
| // hook types (e.g., BoolHook, | ||
| // StringHook) inside evaluation options. | ||
| class BaseHook { | ||
| public: | ||
| BaseHook() = default; | ||
| BaseHook(const BaseHook&) = delete; | ||
| BaseHook(BaseHook&&) = delete; | ||
| BaseHook& operator=(const BaseHook&) = delete; | ||
| BaseHook& operator=(BaseHook&&) = delete; | ||
| virtual ~BaseHook() = default; | ||
| }; | ||
|
|
||
| } // namespace openfeature | ||
|
|
||
| #endif // CPP_SDK_INCLUDE_OPENFEATURE_BASE_HOOK_H_ |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,14 @@ | ||
| #ifndef CPP_SDK_INCLUDE_OPENFEATURE_EVALUATION_OPTIONS_H_ | ||
| #define CPP_SDK_INCLUDE_OPENFEATURE_EVALUATION_OPTIONS_H_ | ||
| #include <memory> | ||
| #include <vector> | ||
|
|
||
| #include "openfeature/base_hook.h" | ||
| #include "openfeature/hook_hints.h" | ||
| namespace openfeature { | ||
| struct EvaluationOptions { | ||
| std::vector<std::shared_ptr<BaseHook>> hooks; | ||
| HookHints hook_hints; | ||
| }; | ||
| } // namespace openfeature | ||
| #endif // CPP_SDK_INCLUDE_OPENFEATURE_EVALUATION_OPTIONS_H_ |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| #include "openfeature/flag_evaluation_details.h" | ||
|
|
||
| #include <optional> | ||
| #include <string> | ||
| #include <string_view> | ||
|
|
||
| #include "openfeature/error_code.h" | ||
| #include "openfeature/flag_metadata.h" | ||
| #include "openfeature/reason.h" | ||
| #include "openfeature/resolution_details.h" | ||
| #include "openfeature/value.h" | ||
|
|
||
| namespace openfeature { | ||
|
|
||
| template <typename T> | ||
| FlagEvaluationDetails<T>::FlagEvaluationDetails( | ||
| std::string flag_key, T value, Reason reason, | ||
| std::optional<std::string> variant, const FlagMetadata& flag_metadata, | ||
| std::optional<ErrorCode> error_code, | ||
| std::optional<std::string> error_message) | ||
| : ResolutionDetails<T>(std::move(value), reason, std::move(variant), | ||
| flag_metadata, error_code, std::move(error_message)), | ||
| flag_key_(std::move(flag_key)) {} | ||
|
|
||
| template <typename T> | ||
| FlagEvaluationDetails<T>::FlagEvaluationDetails( | ||
| std::string flag_key, const ResolutionDetails<T>& resolution_details) | ||
| : ResolutionDetails<T>(resolution_details), | ||
| flag_key_(std::move(flag_key)) {} | ||
|
|
||
| template <typename T> | ||
| std::string_view FlagEvaluationDetails<T>::GetFlagKey() const { | ||
| return flag_key_; | ||
| } | ||
|
|
||
| template class FlagEvaluationDetails<bool>; | ||
| template class FlagEvaluationDetails<std::string>; | ||
| template class FlagEvaluationDetails<int64_t>; | ||
| template class FlagEvaluationDetails<double>; | ||
| template class FlagEvaluationDetails<Value>; | ||
|
|
||
| } // namespace openfeature | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,48 @@ | ||
| #ifndef CPP_SDK_INCLUDE_OPENFEATURE_FLAG_EVALUATION_DETAILS_H_ | ||
| #define CPP_SDK_INCLUDE_OPENFEATURE_FLAG_EVALUATION_DETAILS_H_ | ||
|
|
||
| #include <optional> | ||
| #include <string> | ||
| #include <string_view> | ||
|
|
||
| #include "openfeature/error_code.h" | ||
| #include "openfeature/flag_metadata.h" | ||
| #include "openfeature/reason.h" | ||
| #include "openfeature/resolution_details.h" | ||
| #include "openfeature/value.h" | ||
|
|
||
| namespace openfeature { | ||
|
|
||
| template <typename T> | ||
| class FlagEvaluationDetails : public ResolutionDetails<T> { | ||
| public: | ||
| FlagEvaluationDetails( | ||
| std::string flag_key, T value, Reason reason, | ||
| std::optional<std::string> variant, const FlagMetadata& flag_metadata, | ||
| std::optional<ErrorCode> error_code = std::nullopt, | ||
| std::optional<std::string> error_message = std::nullopt); | ||
|
|
||
| FlagEvaluationDetails(std::string flag_key, | ||
| const ResolutionDetails<T>& resolution_details); | ||
|
|
||
| FlagEvaluationDetails(const FlagEvaluationDetails&) = default; | ||
| FlagEvaluationDetails& operator=(const FlagEvaluationDetails&) = default; | ||
| FlagEvaluationDetails(FlagEvaluationDetails&&) noexcept = default; | ||
| FlagEvaluationDetails& operator=(FlagEvaluationDetails&&) noexcept = default; | ||
| ~FlagEvaluationDetails() = default; | ||
| std::string_view GetFlagKey() const; | ||
|
|
||
| private: | ||
| std::string flag_key_; | ||
| }; | ||
|
|
||
| // Type aliases for common types. | ||
| using BoolFlagEvaluationDetails = FlagEvaluationDetails<bool>; | ||
| using StringFlagEvaluationDetails = FlagEvaluationDetails<std::string>; | ||
| using IntFlagEvaluationDetails = FlagEvaluationDetails<int64_t>; | ||
| using DoubleFlagEvaluationDetails = FlagEvaluationDetails<double>; | ||
| using ObjectFlagEvaluationDetails = FlagEvaluationDetails<Value>; | ||
|
|
||
| } // namespace openfeature | ||
|
|
||
| #endif // CPP_SDK_INCLUDE_OPENFEATURE_FLAG_EVALUATION_DETAILS_H_ |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,12 @@ | ||
| #include "openfeature/hook.h" | ||
|
|
||
| namespace openfeature { | ||
|
|
||
| // Explicit template instantiations for common hook types. | ||
| template class Hook<bool>; | ||
| template class Hook<std::string>; | ||
| template class Hook<int64_t>; | ||
| template class Hook<double>; | ||
| template class Hook<Value>; | ||
|
|
||
| } // namespace openfeature |
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,66 @@ | ||||||||||||||||||||||
| #ifndef CPP_SDK_INCLUDE_OPENFEATURE_HOOK_H_ | ||||||||||||||||||||||
| #define CPP_SDK_INCLUDE_OPENFEATURE_HOOK_H_ | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| #include <cstdint> | ||||||||||||||||||||||
| #include <exception> | ||||||||||||||||||||||
| #include <optional> | ||||||||||||||||||||||
| #include <string> | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| #include "openfeature/base_hook.h" | ||||||||||||||||||||||
| #include "openfeature/evaluation_context.h" | ||||||||||||||||||||||
| #include "openfeature/flag_evaluation_details.h" | ||||||||||||||||||||||
| #include "openfeature/hook_context.h" | ||||||||||||||||||||||
| #include "openfeature/hook_hints.h" | ||||||||||||||||||||||
| #include "openfeature/value.h" | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| namespace openfeature { | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Hook allows application developers to add arbitrary behavior to the | ||||||||||||||||||||||
| // flag evaluation lifecycle. Hooks operate similarly to middleware in web | ||||||||||||||||||||||
| // frameworks. They are executed stack-wise with respect to flag resolution, | ||||||||||||||||||||||
| // prioritizing increasing specificity (API, Client, Invocation, Provider) | ||||||||||||||||||||||
| // first, and the order in which they were added second. | ||||||||||||||||||||||
| /// https://openfeature.dev/specification/sections/hooks | ||||||||||||||||||||||
| template <typename T> | ||||||||||||||||||||||
| class Hook : public BaseHook { | ||||||||||||||||||||||
| public: | ||||||||||||||||||||||
| Hook() = default; | ||||||||||||||||||||||
| Hook(const Hook&) = delete; | ||||||||||||||||||||||
| Hook& operator=(const Hook&) = delete; | ||||||||||||||||||||||
| Hook(Hook&&) = delete; | ||||||||||||||||||||||
| Hook& operator=(Hook&&) = delete; | ||||||||||||||||||||||
| ~Hook() override = default; | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Runs before the flag evaluation occurs. | ||||||||||||||||||||||
| virtual std::optional<EvaluationContext> Before(HookContext<T>& ctx, | ||||||||||||||||||||||
| const HookHints& hints) { | ||||||||||||||||||||||
| return std::nullopt; | ||||||||||||||||||||||
| } | ||||||||||||||||||||||
|
Comment on lines
+34
to
+38
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win Use a const reference for The OpenFeature specification requires the hook context to be immutable. Passing Change the signature to accept 🛠️ Proposed fixes for the interface and testUpdate the signature in this file: // Runs before the flag evaluation occurs.
- virtual std::optional<EvaluationContext> Before(HookContext<T>& ctx,
+ virtual std::optional<EvaluationContext> Before(const HookContext<T>& ctx,
const HookHints& hints) {
return std::nullopt;
}You will also need to update the corresponding override in - std::optional<EvaluationContext> Before(HookContext<T>& ctx,
+ std::optional<EvaluationContext> Before(const HookContext<T>& ctx,
const HookHints& hints) override {📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Runs immediately after successful flag evaluation occurs. | ||||||||||||||||||||||
| virtual void After(const HookContext<T>& ctx, | ||||||||||||||||||||||
| const FlagEvaluationDetails<T>& details, | ||||||||||||||||||||||
| const HookHints& hints) {} | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Runs if an error occurs during flag evaluation or in `Before`/`After` | ||||||||||||||||||||||
| // stages. | ||||||||||||||||||||||
| virtual void Error(const HookContext<T>& ctx, const std::exception& error, | ||||||||||||||||||||||
| const HookHints& hints) {} | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Runs after the flag evaluation occurs, regardless of whether it was | ||||||||||||||||||||||
| // successful or not. | ||||||||||||||||||||||
| virtual void Finally(const HookContext<T>& ctx, | ||||||||||||||||||||||
| const FlagEvaluationDetails<T>& details, | ||||||||||||||||||||||
| const HookHints& hints) {} | ||||||||||||||||||||||
| }; | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| // Type aliases for common hook specializations. | ||||||||||||||||||||||
| using BoolHook = Hook<bool>; | ||||||||||||||||||||||
| using StringHook = Hook<std::string>; | ||||||||||||||||||||||
| using IntHook = Hook<int64_t>; | ||||||||||||||||||||||
| using DoubleHook = Hook<double>; | ||||||||||||||||||||||
| using ObjectHook = Hook<Value>; | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| } // namespace openfeature | ||||||||||||||||||||||
|
|
||||||||||||||||||||||
| #endif // CPP_SDK_INCLUDE_OPENFEATURE_HOOK_H_ | ||||||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win
Include
<utility>forstd::move.The
std::moveutility is used heavily in this file, but<utility>is not explicitly included. Relying on transitive includes can lead to compilation failures across different compilers or standard library versions.🛠️ Proposed fix
`#include` <optional> `#include` <string> `#include` <string_view> +#include <utility>📝 Committable suggestion
🤖 Prompt for AI Agents