22#include "rpc/common/APIVersion.hpp"
23#include "util/config/Error.hpp"
24#include "util/config/Types.hpp"
25#include "util/log/Logger.hpp"
27#include <fmt/format.h>
28#include <fmt/ranges.h>
41namespace util::config {
48static constexpr std::array<std::string_view, 6> kLOG_LEVELS = {
60static constexpr std::array<std::string_view, 5> kLOG_TAGS = {
71static constexpr std::array<std::string_view, 3> kLOAD_CACHE_MODE = {
80static constexpr std::array<std::string_view, 1> kDATABASE_TYPE = {
"cassandra"};
85static constexpr std::array<std::string_view, 2> kPROCESSING_POLICY = {
"parallel",
"sequent"};
90static constexpr std::array<std::string_view, 2> kPROVIDER = {
"cassandra",
"aws_keyspace"};
109 if (
auto const maybeError =
checkTypeImpl(val); maybeError.has_value())
125 template <std::
size_t ArrSize>
126 constexpr std::string
128 std::string_view key,
130 std::array<std::string_view, ArrSize> arr
134 auto const valueStr = std::visit([](
auto const& v) {
return fmt::format(
"{}", v); }, value);
138 R
"(You provided value "{}". Key "{}"'s value must be one of the following: {})",
151 virtual std::optional<Error>
160 virtual std::optional<Error>
169 print(std::ostream& stream)
const = 0;
200 [[nodiscard]] std::optional<Error>
201 checkTypeImpl(Value
const& port)
const override;
209 [[nodiscard]] std::optional<Error>
210 checkValueImpl(Value
const& port)
const override;
218 print(std::ostream& stream)
const override
220 stream << fmt::format(
221 "The minimum value is `{}`. The maximum value is `{}`.", kPORT_MIN, kPORT_MAX
225 static constexpr uint32_t kPORT_MIN = 1;
226 static constexpr uint32_t kPORT_MAX = 65535;
243 [[nodiscard]] std::optional<Error>
244 checkTypeImpl(Value
const& ip)
const override;
252 [[nodiscard]] std::optional<Error>
253 checkValueImpl(Value
const& ip)
const override;
261 print(std::ostream& stream)
const override
263 stream <<
"The value must be a valid IP address.";
273template <std::
size_t ArrSize>
283 constexpr OneOf(std::string_view key, std::array<std::string_view, ArrSize> arr)
284 : key_{key}, arr_{arr}
288 constexpr ~OneOf() noexcept override = default;
297 [[nodiscard]] std::optional<
Error>
298 checkTypeImpl(Value const& val)
const override
300 if (!std::holds_alternative<std::string>(val))
301 return Error{fmt::format(R
"(Key "{}"'s value must be a string)", key_)};
311 [[nodiscard]] std::optional<Error>
312 checkValueImpl(Value
const& val)
const override
314 namespace rg = std::ranges;
315 auto const check = [&val](std::string_view name) {
316 return std::get<std::string>(val) == name;
318 if (rg::any_of(arr_, check))
330 print(std::ostream& stream)
const override
332 std::string valuesStream;
333 std::ranges::for_each(arr_, [&valuesStream](std::string_view elem) {
334 valuesStream += fmt::format(
" `{}`,", elem);
337 valuesStream.back() =
'.';
338 stream << fmt::format(
"The value must be one of the following:{}", valuesStream);
341 std::string_view key_;
342 std::array<std::string_view, ArrSize> arr_;
348template <
typename NumType>
370 [[nodiscard]] std::optional<
Error>
371 checkTypeImpl(Value const& num)
const override
373 if (!std::holds_alternative<int64_t>(num))
374 return Error{
"Number must be of type integer"};
384 [[nodiscard]] std::optional<Error>
385 checkValueImpl(Value
const& num)
const override
387 auto const numValue = std::get<int64_t>(num);
388 if (numValue >=
static_cast<int64_t
>(min_) && numValue <=
static_cast<int64_t
>(max_))
390 return Error{fmt::format(
"Number must be between {} and {}", min_, max_)};
399 print(std::ostream& stream)
const override
401 stream << fmt::format(
"The minimum value is `{}`. The maximum value is `{}`.", min_, max_);
422 [[nodiscard]] std::optional<Error>
423 checkTypeImpl(Value
const& num)
const override;
431 [[nodiscard]] std::optional<Error>
432 checkValueImpl(Value
const& num)
const override;
440 print(std::ostream& stream)
const override
442 stream <<
"The value must be a positive double number.";
457 [[nodiscard]] std::optional<Error>
458 checkTypeImpl(Value
const& value)
const override;
466 [[nodiscard]] std::optional<Error>
467 checkValueImpl(Value
const& value)
const override;
475 print(std::ostream& stream)
const override
477 stream <<
"Checks whether provided RPC name is valid";
482static constinit ValidIPConstraint gValidateIp{};
484static constinit OneOf gValidateChannelName{
"channel", Logger::kCHANNELS};
485static constinit OneOf gValidateLogLevelName{
"log.level", kLOG_LEVELS};
486static constinit OneOf gValidateCassandraName{
"database.type", kDATABASE_TYPE};
487static constinit OneOf gValidateLoadMode{
"cache.load", kLOAD_CACHE_MODE};
488static constinit OneOf gValidateLogTag{
"log.tag_style", kLOG_TAGS};
489static constinit OneOf gValidateProcessingPolicy{
"server.processing_policy", kPROCESSING_POLICY};
490static constinit OneOf gValidateProvider{
"database.cassandra.provider", kPROVIDER};
497 std::numeric_limits<uint16_t>::max()
503 std::numeric_limits<uint16_t>::max()
508 std::numeric_limits<uint16_t>::max()
513 std::numeric_limits<uint32_t>::max()
517 std::numeric_limits<uint32_t>::max()
Represents the config values for Json/Yaml config.
Definition ConfigValue.hpp:47
An interface to enforce constraints on certain values within ClioConfigDefinition.
Definition ConfigConstraints.hpp:95
friend std::ostream & operator<<(std::ostream &stream, Constraint const &cons)
Custom output stream for constraint.
Definition ConfigConstraints.hpp:179
virtual void print(std::ostream &stream) const =0
Prints to the output stream for this specific constraint.
virtual std::optional< Error > checkValueImpl(Value const &val) const =0
Check if the value is within the constraint.
constexpr std::string makeErrorMsg(std::string_view key, Value const &value, std::array< std::string_view, ArrSize > arr) const
Creates an error message for all constraints that must satisfy certain hard-coded values.
Definition ConfigConstraints.hpp:127
std::optional< Error > checkConstraint(Value const &val) const
Check if the value meets the specific constraint.
Definition ConfigConstraints.hpp:107
virtual std::optional< Error > checkTypeImpl(Value const &val) const =0
Check if the value is of a correct type for the constraint.
A constraint class to ensure an integer value is between two numbers (inclusive).
Definition ConfigConstraints.hpp:349
constexpr NumberValueConstraint(NumType min, NumType max)
Constructs a constraint where the number must be between min_ and max_.
Definition ConfigConstraints.hpp:357
A constraint class to ensure the provided value is one of the specified values in an array.
Definition ConfigConstraints.hpp:274
constexpr OneOf(std::string_view key, std::array< std::string_view, ArrSize > arr)
Constructs a constraint where the value must be one of the values in the provided array.
Definition ConfigConstraints.hpp:283
A constraint to ensure the port number is within a valid range.
Definition ConfigConstraints.hpp:189
A constraint to ensure a double number is positive.
Definition ConfigConstraints.hpp:411
A constraint to ensure the value is a valid RPC command name.
Definition ConfigConstraints.hpp:449
A constraint to ensure the IP address is valid.
Definition ConfigConstraints.hpp:232
Provides view into ConfigValues that represents values in Clio Config.
Definition ValueView.hpp:46
static constexpr uint32_t kAPI_VERSION_MIN
Minimum API version supported by this build.
Definition APIVersion.hpp:38
static constexpr uint32_t kAPI_VERSION_MAX
Maximum API version supported by this build.
Definition APIVersion.hpp:43
Displays the different errors when parsing user config.
Definition Error.hpp:31