├── .gitignore ├── CMakeLists.txt ├── CONTRIBUTING.md ├── LICENSE.md ├── README.md ├── TODO.md ├── depends.cmake ├── docs ├── builtin_operators.md └── index.md ├── examples ├── CMakeLists.txt ├── example01_validate.cpp ├── example02_validate_with_report.cpp ├── example03_validate_with_exception.cpp ├── example04_apply_validator.cpp ├── example05_dynamic_validator_allocation.cpp ├── example06_nested_validators.cpp ├── example07_nested_members.cpp ├── example08_member_existence.cpp ├── example09_custom_property.cpp ├── example10_custom_property_flag.cpp ├── example11_heterogeneous_property_implicit.cpp ├── example12_heterogeneous_property_explicit.cpp ├── example13_variadic_property.cpp ├── example14_variadic_property_aggregation.cpp ├── example15_operator_in.cpp ├── example16_operator_negation.cpp ├── example17_custom_operator.cpp ├── example18_move_copy.cpp ├── example19_lazy_operands.cpp ├── example20_operand_other_member.cpp ├── example21_operand_sample_object.cpp ├── example22_element_aggregation.cpp ├── example23_tree_validation.cpp ├── example24_partial_validation.cpp ├── example25_validate_evaluation_result.cpp ├── example26_prevalidate_set_member.cpp └── example27_prevalidate_set_custom_property.cpp ├── include └── hatn │ └── validator │ ├── adapter.hpp │ ├── adapters │ ├── adapter_traits_wrapper.hpp │ ├── default_adapter.hpp │ ├── failed_members_adapter.hpp │ ├── impl │ │ ├── default_adapter_impl.hpp │ │ └── intermediate_adapter_traits.hpp │ ├── make_intermediate_adapter.hpp │ ├── prevalidation_adapter.hpp │ └── reporting_adapter.hpp │ ├── aggregation │ ├── aggregation.hpp │ ├── aggregation.ipp │ ├── all.hpp │ ├── and.hpp │ ├── any.hpp │ ├── element_aggregation.hpp │ ├── element_aggregation.ipp │ ├── not.hpp │ ├── or.hpp │ ├── tree.hpp │ ├── wrap_heterogeneous_index.hpp │ ├── wrap_index.hpp │ └── wrap_it.hpp │ ├── apply.hpp │ ├── apply_generated_paths.hpp │ ├── apply_generated_paths.ipp │ ├── apply_member_path.hpp │ ├── apply_member_path.ipp │ ├── base_validator.hpp │ ├── basic_property.hpp │ ├── can_check_contains.hpp │ ├── can_get.hpp │ ├── check_contains.hpp │ ├── check_exists.hpp │ ├── check_member.hpp │ ├── check_member_exists_traits_proxy.hpp │ ├── check_member_path.hpp │ ├── compact_variadic_property.hpp │ ├── config.hpp │ ├── detail │ ├── aggregate_all.hpp │ ├── aggregate_and.hpp │ ├── aggregate_any.hpp │ ├── aggregate_or.hpp │ ├── backend_formatter_helper.hpp │ ├── dispatcher_impl.hpp │ ├── formatter_fmt.hpp │ ├── formatter_std.hpp │ ├── get_impl.hpp │ ├── has_method.hpp │ ├── has_property.hpp │ ├── hint_helper.hpp │ ├── logical_not.hpp │ ├── member_helper.hpp │ ├── member_helper.ipp │ └── reorder_and_present.hpp │ ├── dispatcher.hpp │ ├── embedded_object.hpp │ ├── error.hpp │ ├── extract.hpp │ ├── filter_member.hpp │ ├── filter_path.hpp │ ├── generate_paths.hpp │ ├── get.hpp │ ├── get_member.hpp │ ├── headeronly.cfg │ ├── heterogeneous_property.hpp │ ├── ignore_compiler_warnings.hpp │ ├── interval.hpp │ ├── invoke_member_if_exists.hpp │ ├── lazy.hpp │ ├── make_member.hpp │ ├── make_validator.hpp │ ├── master_sample.hpp │ ├── member.hpp │ ├── member_path.hpp │ ├── member_property.hpp │ ├── member_with_name.hpp │ ├── member_with_name_list.hpp │ ├── operand.hpp │ ├── operators.hpp │ ├── operators │ ├── comparison.hpp │ ├── contains.hpp │ ├── exists.hpp │ ├── flag.hpp │ ├── in.hpp │ ├── invert_op.hpp │ ├── lex_in.hpp │ ├── lexicographical.hpp │ ├── logical.hpp │ ├── number_patterns.hpp │ ├── op_report_without_operand.hpp │ ├── operator.hpp │ ├── regex.hpp │ ├── string_patterns.hpp │ └── wrap_op.hpp │ ├── prepend_super_member.hpp │ ├── prepend_super_member.ipp │ ├── prevalidation │ ├── clear_validated.hpp │ ├── prevalidation_adapter_impl.hpp │ ├── prevalidation_adapter_tag.hpp │ ├── resize_validated.hpp │ ├── set_validated.hpp │ ├── strict_any.hpp │ ├── true_if_empty.hpp │ ├── true_if_size.hpp │ ├── unset_validated.hpp │ ├── validate_empty.hpp │ └── validate_value.hpp │ ├── properties.hpp │ ├── properties │ ├── empty.hpp │ ├── h_size.hpp │ ├── length.hpp │ ├── pair.hpp │ ├── size.hpp │ └── value.hpp │ ├── property.hpp │ ├── property_validator.hpp │ ├── range.hpp │ ├── reporting │ ├── aggregation_strings.hpp │ ├── backend_formatter.hpp │ ├── concrete_phrase.hpp │ ├── decorator.hpp │ ├── dotted_member_names.hpp │ ├── extend_translator.hpp │ ├── failed_members_reporter.hpp │ ├── flag_presets.hpp │ ├── format_bool_operand.hpp │ ├── format_join_grammar_cats.hpp │ ├── format_operand.hpp │ ├── formatter.hpp │ ├── grammar_categories.hpp │ ├── locale │ │ ├── ru.hpp │ │ └── sample_locale.hpp │ ├── mapped_translator.hpp │ ├── member_names.hpp │ ├── member_operand.hpp │ ├── nested_member_name.hpp │ ├── no_translator.hpp │ ├── operand_formatter.hpp │ ├── order_and_presentation.hpp │ ├── original_member_names.hpp │ ├── phrase_grammar_cats.hpp │ ├── phrase_translator.hpp │ ├── prepare_operand_for_formatter.hpp │ ├── prepare_property_formatting.hpp │ ├── property_member_name.hpp │ ├── quotes_decorator.hpp │ ├── report_aggregation.hpp │ ├── reporter.hpp │ ├── reporter_with_object_name.hpp │ ├── reporting_adapter_impl.hpp │ ├── single_member_name.hpp │ ├── strings.hpp │ ├── translate.hpp │ ├── translator.hpp │ └── translator_repository.hpp │ ├── status.hpp │ ├── utils │ ├── adjust_storable_ignore.hpp │ ├── adjust_storable_type.hpp │ ├── class_method_args.hpp │ ├── conditional_fold.hpp │ ├── copy.hpp │ ├── enable_to_string.hpp │ ├── feature_bitmask.hpp │ ├── foreach_if.hpp │ ├── get_it.hpp │ ├── hana_to_std_tuple.hpp │ ├── has_reset.hpp │ ├── heterogeneous_size.hpp │ ├── invoke_and.hpp │ ├── invoke_or.hpp │ ├── is_container.hpp │ ├── is_pair.hpp │ ├── make_types_tuple.hpp │ ├── object_wrapper.hpp │ ├── optional.hpp │ ├── pointer_as_reference.hpp │ ├── reference_wrapper.hpp │ ├── safe_compare.hpp │ ├── string_view.hpp │ ├── to_string.hpp │ ├── unwrap_object.hpp │ ├── value_as_container.hpp │ └── wrap_object.hpp │ ├── validate.hpp │ ├── validator.hpp │ ├── validators.hpp │ ├── value_transformer.hpp │ ├── variadic_arg.hpp │ ├── variadic_arg_tag.hpp │ ├── variadic_property.hpp │ ├── version.hpp │ └── with_check_member_exists.hpp ├── sample-build ├── linux-clang.sh ├── readme.txt └── win-msvc.bat └── test ├── CMakeLists.txt ├── main.cpp ├── test.cmake ├── testallanyreport.cpp ├── testclearvalidated.cpp ├── testfmtformatter.cpp ├── testformatter.cpp ├── testhabrexamples_ru.cpp ├── testheterogeneouscontainers.cpp ├── testinvokeandor.cpp ├── testlexicographical.cpp ├── testnestedallany.cpp ├── testnestedvalidators.cpp ├── testnomemberreporting.cpp ├── testoperatorexists.cpp ├── testoperatorin.cpp ├── testpartialpaths.cpp ├── testpointers.cpp ├── testprevalidation.cpp ├── testregex.cpp ├── testreporter.cpp ├── testreporting.cpp ├── testreportinghints.cpp ├── testresizevalidated.cpp ├── testsetvalidated.cpp ├── teststdformatter.cpp ├── teststrings.cpp ├── teststrnumbers.cpp ├── testtranslator.cpp ├── testtranslator_ru.cpp ├── testtree.cpp ├── testunsetvalidated.cpp ├── testvalidate.cpp ├── testvalidator.cpp ├── testvalidatorimpl.cpp ├── testvalidatoronheap.cpp ├── testvaluetransformer.cpp └── testvariadicproperty.cpp /.gitignore: -------------------------------------------------------------------------------- 1 | CMakeLists.txt.user 2 | __pycache__ 3 | *.pyc 4 | .DS_Store 5 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing to cpp-validator 2 | 3 | By submitting a pull request or a patch, you represent that you have the right to license your contribution to the cpp-validator project owners and the community, agree that your contributions are licensed under the cpp-validator license, and agree to future changes to the licensing. 4 | 5 | All C++ code should adhere to [Boost Library Requirements and Guidelines](https://www.boost.org/development/requirements.html#Guidelines). 6 | 7 | Thanks for contributing! -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | Boost Software License - Version 1.0 - August 17th, 2003 2 | 3 | Permission is hereby granted, free of charge, to any person or organization 4 | obtaining a copy of the software and accompanying documentation covered by 5 | this license (the "Software") to use, reproduce, display, distribute, 6 | execute, and transmit the Software, and to prepare derivative works of the 7 | Software, and to permit third-parties to whom the Software is furnished to 8 | do so, all subject to the following: 9 | 10 | The copyright notices in the Software and this entire statement, including 11 | the above license grant, this restriction and the following disclaimer, 12 | must be included in all copies of the Software, in whole or in part, and 13 | all derivative works of the Software, unless such copies or derivative 14 | works are solely in the form of machine-executable object code generated by 15 | a source language processor. 16 | 17 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 18 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 19 | FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT 20 | SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE 21 | FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, 22 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 23 | DEALINGS IN THE SOFTWARE. 24 | -------------------------------------------------------------------------------- /TODO.md: -------------------------------------------------------------------------------- 1 | - Refactor formatting of variadic properties with taking into account preceding grammar categories. 2 | - Check prevalidation with variadic properties, heterogeneous containers and trees. 3 | - Implement filtering with predicates in element aggregation. 4 | -------------------------------------------------------------------------------- /depends.cmake: -------------------------------------------------------------------------------- 1 | SET(THIRDPARTY_ENABLE_FMT ON CACHE BOOL "Enable libfmt") 2 | MESSAGE (STATUS "Enable libfmt") 3 | -------------------------------------------------------------------------------- /examples/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | PROJECT(hatnvalidator-examples) 2 | 3 | SET(SOURCES 4 | example01_validate.cpp 5 | example02_validate_with_report.cpp 6 | example03_validate_with_exception.cpp 7 | example04_apply_validator.cpp 8 | example05_dynamic_validator_allocation.cpp 9 | example06_nested_validators.cpp 10 | example07_nested_members.cpp 11 | example08_member_existence.cpp 12 | example09_custom_property.cpp 13 | example10_custom_property_flag.cpp 14 | example11_heterogeneous_property_implicit.cpp 15 | example12_heterogeneous_property_explicit.cpp 16 | example13_variadic_property.cpp 17 | example14_variadic_property_aggregation.cpp 18 | example15_operator_in.cpp 19 | example16_operator_negation.cpp 20 | example17_custom_operator.cpp 21 | example18_move_copy.cpp 22 | example19_lazy_operands.cpp 23 | example20_operand_other_member.cpp 24 | example21_operand_sample_object.cpp 25 | example22_element_aggregation.cpp 26 | example23_tree_validation.cpp 27 | example24_partial_validation.cpp 28 | example25_validate_evaluation_result.cpp 29 | example26_prevalidate_set_member.cpp 30 | example27_prevalidate_set_custom_property.cpp 31 | ) 32 | 33 | ENABLE_TESTING(true) 34 | FOREACH(SRC ${SOURCES} ) 35 | STRING(REPLACE ".cpp" "" EXEC_NAME ${SRC}) 36 | ADD_EXECUTABLE(${EXEC_NAME} ${CMAKE_CURRENT_SOURCE_DIR}/${SRC}) 37 | TARGET_LINK_LIBRARIES(${EXEC_NAME} hatnvalidator) 38 | 39 | ADD_TEST(NAME ${EXEC_NAME} COMMAND ${EXEC_NAME}) 40 | SET_TESTS_PROPERTIES(${EXEC_NAME} PROPERTIES LABELS "examples") 41 | ENDFOREACH() 42 | -------------------------------------------------------------------------------- /examples/example01_validate.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | 10 | // define validator 11 | auto v=validator(gt,100); // value must be greater than 100 12 | 13 | // validate variables 14 | error err; 15 | 16 | validate(90,v,err); 17 | assert(err); // validation failed, 90 is less than 100 18 | 19 | validate(200,v,err); 20 | assert(!err); // validation succeeded, 200 is greater than 100 21 | 22 | std::cout << "Example 1 done" << std::endl; 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /examples/example02_validate_with_report.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // define validator 10 | auto v=validator(gt,100); 11 | 12 | // validate variables 13 | error_report err; 14 | 15 | // validate good value 16 | validate(90,v,err); 17 | if (err) 18 | { 19 | std::cerr << "Validation for 90 failed: " << err.message() << std::endl; 20 | } 21 | assert(err); 22 | 23 | // validate bad value 24 | validate(200,v,err); 25 | if (!err) 26 | { 27 | std::cout << "Validation for 200 succeeded" << std::endl; 28 | } 29 | assert(!err); 30 | 31 | std::cout << "Example 2 done" << std::endl; 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /examples/example03_validate_with_exception.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // define validator 10 | auto v=validator(gt,100); 11 | 12 | // validate good value 13 | try 14 | { 15 | validate(200,v); 16 | std::cout << "Validation for 200 succeeded" << std::endl; 17 | } 18 | catch (const validation_error&) 19 | { 20 | } 21 | 22 | // validate bad value 23 | try 24 | { 25 | validate(90,v); 26 | std::cout << "Never reaches this point" << std::endl; 27 | assert(false); 28 | } 29 | catch (const validation_error& err) 30 | { 31 | std::cerr << "Validation for 90 failed: " << err.what() << std::endl; 32 | } 33 | 34 | std::cout << "Example 3 done" << std::endl; 35 | return 0; 36 | } 37 | -------------------------------------------------------------------------------- /examples/example04_apply_validator.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | using namespace HATN_VALIDATOR_NAMESPACE; 5 | 6 | int main() 7 | { 8 | // define validator 9 | auto v=validator(gt,100); 10 | 11 | // validate variable that satisfies validator 12 | int value1=200; 13 | auto a1=make_default_adapter(value1); 14 | assert(v.apply(a1)); // apply to adapter 15 | assert(v.apply(value1)); // apply to value 16 | 17 | // validate variable that doesn't satisfy validator 18 | int value2=90; 19 | auto a2=make_default_adapter(value2); 20 | assert(!v.apply(a2)); // apply to adapter 21 | assert(!v.apply(value2)); // apply to value 22 | 23 | std::cout << "Example 4 done" << std::endl; 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /examples/example05_dynamic_validator_allocation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // create raw pointer validator 10 | auto raw_pointer_validator=new_validator( 11 | _["field1"](eq,1) 12 | ); 13 | 14 | // create shared pointer validator 15 | auto shared_pointer_validator=shared_validator( 16 | _["field1"](eq,1) 17 | ); 18 | 19 | // validate check_var with validators 20 | std::map check_var={{"field1",1}}; 21 | 22 | assert(raw_pointer_validator->apply(check_var)); 23 | assert(shared_pointer_validator->apply(check_var)); 24 | 25 | // delete raw pointer validator 26 | delete raw_pointer_validator; 27 | 28 | std::cout << "Example 5 done" << std::endl; 29 | return 0; 30 | } 31 | -------------------------------------------------------------------------------- /examples/example06_nested_validators.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | int main() 10 | { 11 | // plain validator 12 | auto validator_of_sets=validator( 13 | _["level2"](exists,true) 14 | ); 15 | // nested validator 16 | auto validator_of_maps_of_sets=validator( 17 | _["level1"](validator_of_sets) 18 | ); 19 | 20 | // apply validator to nested container that satisfies validation conditions 21 | std::map> map_of_sets1{ 22 | {"level1",{"level2"}} 23 | }; 24 | assert(validator_of_maps_of_sets.apply(map_of_sets1)); 25 | 26 | // apply validator to nested container that does not satisfy validation conditions 27 | std::map> map_of_sets2{ 28 | {"level1",{"level2_1"}} 29 | }; 30 | assert(!validator_of_maps_of_sets.apply(map_of_sets2)); 31 | 32 | std::cout << "Example 6 done" << std::endl; 33 | return 0; 34 | } 35 | -------------------------------------------------------------------------------- /examples/example07_nested_members.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | int main() 9 | { 10 | auto v=validator( 11 | _["field1"][1](in,range({10,20,30,40,50})), 12 | _["field1"][2](lt,100), 13 | _["field2"](exists,false), 14 | _["field3"](empty(flag,true)) 15 | ); 16 | 17 | std::string report; 18 | 19 | std::map> nested_map={ 20 | {"field1",{{1,5},{2,50}}}, 21 | {"field3",{}} 22 | }; 23 | auto ra=make_reporting_adapter(nested_map,report); 24 | 25 | if (!v.apply(ra)) 26 | { 27 | std::cerr << report << std::endl; 28 | /* prints: 29 | "element #1 of field1 must be in range [10, 20, 30, 40, 50]" 30 | */ 31 | } 32 | assert(!v.apply(ra)); 33 | 34 | std::cout << "Example 7 done" << std::endl; 35 | return 0; 36 | } 37 | -------------------------------------------------------------------------------- /examples/example08_member_existence.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | std::map m1={ 10 | {"field1",10}, 11 | {"field3",100} 12 | }; 13 | 14 | // adapter 1 aborts validation if some member is not found 15 | auto a1=make_default_adapter(m1); 16 | a1.set_check_member_exists_before_validation(true); 17 | a1.set_unknown_member_mode(if_member_not_found::abort); 18 | 19 | // adapter 2 ignores not found members 20 | auto a2=make_default_adapter(m1); 21 | a2.set_check_member_exists_before_validation(true); 22 | a2.set_unknown_member_mode(if_member_not_found::ignore); 23 | 24 | // both members exist in the map 25 | auto v1=validator( 26 | _["field1"](gte,9), 27 | _["field3"](eq,100) 28 | ); 29 | // validation succeeded with both adapters 30 | assert(v1.apply(a1)); 31 | assert(v1.apply(a2)); 32 | 33 | // member "field2" doesn't exist in the map 34 | auto v2=validator( 35 | _["field1"](eq,10), 36 | _["field2"](lt,1000) 37 | ); 38 | // validation failed with adapter 1 39 | assert(!v2.apply(a1)); 40 | // validation succeeded with adapter 2 41 | assert(v2.apply(a2)); 42 | 43 | std::cout << "Example 8 done" << std::endl; 44 | return 0; 45 | } 46 | -------------------------------------------------------------------------------- /examples/example09_custom_property.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | // structure with two properties 8 | struct Foo 9 | { 10 | // member variable 11 | std::string var1; 12 | 13 | // getter method 14 | uint32_t get_var2() const 15 | { 16 | return _var2; 17 | } 18 | 19 | private: 20 | 21 | uint32_t _var2=1000; 22 | }; 23 | 24 | // define property corresponding to member variable 25 | HATN_VALIDATOR_PROPERTY(var1); 26 | 27 | // define property corresponding to getter method 28 | HATN_VALIDATOR_PROPERTY(get_var2); 29 | 30 | int main() 31 | { 32 | // validator with custom properties 33 | auto v=validator( 34 | var1(ne,"unknown"), 35 | get_var2(gte,100) 36 | ); 37 | 38 | // valiate object 39 | Foo foo_instance; 40 | assert(v.apply(foo_instance)); 41 | 42 | std::cout << "Example 9 done" << std::endl; 43 | return 0; 44 | } 45 | -------------------------------------------------------------------------------- /examples/example10_custom_property_flag.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | // structure with red_color() getter method 10 | struct Foo 11 | { 12 | // boolean getter method 13 | bool red_color() const 14 | { 15 | return true; 16 | } 17 | }; 18 | 19 | // define flaggable red_color property 20 | HATN_VALIDATOR_PROPERTY_FLAG(red_color,"Must be red","Must be not red") 21 | 22 | int main() 23 | { 24 | // validator with red_color property 25 | auto v=validator( 26 | _[red_color](flag,false) 27 | ); 28 | 29 | // create reporting adapter 30 | std::string report; 31 | Foo foo_instance; 32 | auto ra=make_reporting_adapter(foo_instance,report); 33 | 34 | // apply validator and print report 35 | if (!v.apply(ra)) 36 | { 37 | std::cerr << report << std::endl; 38 | /* prints: 39 | 40 | "Must be not red" 41 | 42 | */ 43 | } 44 | assert(!v.apply(ra)); 45 | 46 | std::cout << "Example 10 done" << std::endl; 47 | return 0; 48 | } 49 | -------------------------------------------------------------------------------- /examples/example11_heterogeneous_property_implicit.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | int main() 10 | { 11 | // implicit heterogeneous property from std::integral_constant 12 | auto v1=validator( 13 | _[std::integral_constant{}](gt,100) 14 | ); 15 | // implicit heterogeneous property from hana::size_c 16 | auto v2=validator( 17 | _[hana::size_c<1>](gt,100) 18 | ); 19 | 20 | error_report err; 21 | 22 | // validate std::tuple 23 | auto t1=std::make_tuple(200,50,"hello"); 24 | validate(t1,v1,err); 25 | assert(err); 26 | assert(err.message()==std::string("element #1 must be greater than 100")); 27 | 28 | // validate hana::tuple 29 | auto t2=hana::make_tuple(200,50,"hello"); 30 | validate(t2,v2,err); 31 | assert(err); 32 | assert(err.message()==std::string("element #1 must be greater than 100")); 33 | 34 | std::cout << "Example 11 done" << std::endl; 35 | return 0; 36 | } 37 | -------------------------------------------------------------------------------- /examples/example12_heterogeneous_property_explicit.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | // define property "zero" with index 0 10 | HATN_VALIDATOR_HETEROGENEOUS_PROPERTY(zero,0) 11 | // define property "one" with index 1 12 | HATN_VALIDATOR_HETEROGENEOUS_PROPERTY(one,1) 13 | 14 | int main() 15 | { 16 | // use explicit heterogeneous property "one" 17 | auto v1=validator( 18 | _[one](gt,100) 19 | ); 20 | // use explicit heterogeneous property "zero" 21 | auto v2=validator( 22 | _[zero](lt,100) 23 | ); 24 | 25 | error_report err; 26 | 27 | auto t1=std::make_tuple(200,50,"hello"); 28 | validate(t1,v1,err); 29 | assert(err); 30 | std::cerr << err.message() << std::endl; 31 | assert(err.message()==std::string("one must be greater than 100")); 32 | 33 | auto t2=hana::make_tuple(200,50,"hello"); 34 | validate(t2,v2,err); 35 | assert(err); 36 | std::cerr << err.message() << std::endl; 37 | assert(err.message()==std::string("zero must be less than 100")); 38 | 39 | std::cout << "Example 12 done" << std::endl; 40 | return 0; 41 | } 42 | -------------------------------------------------------------------------------- /examples/example13_variadic_property.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | // define a structure with variadic properties 9 | struct WithChild 10 | { 11 | // method with one argument 12 | int child(int val) const noexcept 13 | { 14 | return val+1; 15 | } 16 | 17 | // method with two arguments 18 | int child_word(int val, const std::string& word) const noexcept 19 | { 20 | return val+static_cast(word.size()); 21 | } 22 | 23 | // method to check if object "has" child_world with provided arguments 24 | bool has_child_word(int val, const std::string& word) const noexcept 25 | { 26 | return val>10 && word.size()>=5; 27 | } 28 | }; 29 | 30 | // define variadic property 31 | HATN_VALIDATOR_VARIADIC_PROPERTY(child) 32 | // define variadic property to be used as "exists" checker 33 | HATN_VALIDATOR_VARIADIC_PROPERTY(has_child_word) 34 | // define variadic property with "exists" checker 35 | HATN_VALIDATOR_VARIADIC_PROPERTY_HAS(child_word,has_child_word) 36 | 37 | int main() 38 | { 39 | // define object 40 | WithChild o1; 41 | 42 | // define validation adapter with text reports 43 | std::string rep; 44 | auto ra1=make_reporting_adapter(o1,rep); 45 | 46 | // variadic property with single argument and member notation 47 | auto v1=validator( 48 | _[child][varg(1)](eq,30) 49 | ); 50 | assert(!v1.apply(ra1)); 51 | assert(rep==std::string("child(1) must be equal to 30")); 52 | rep.clear(); 53 | 54 | // variadic property with single argument and property notation 55 | auto v2=validator( 56 | child(1)(eq,30) 57 | ); 58 | assert(!v2.apply(ra1)); 59 | assert(rep==std::string("child(1) must be equal to 30")); 60 | rep.clear(); 61 | 62 | // variadic property with two arguments and member notation 63 | auto v3=validator( 64 | _[child_word][varg(20)][varg("hello")](eq,30) 65 | ); 66 | assert(!v3.apply(ra1)); 67 | assert(rep==std::string("child_word(20,hello) must be equal to 30")); 68 | rep.clear(); 69 | 70 | // variadic property with two arguments and property notation 71 | auto v4=validator( 72 | child_word(20,"hello")(eq,30) 73 | ); 74 | assert(!v4.apply(ra1)); 75 | assert(rep==std::string("child_word(20,hello) must be equal to 30")); 76 | rep.clear(); 77 | 78 | // check if variadic property exists 79 | auto v5=validator( 80 | _[child_word][20]["hello"](exists,true) 81 | ); 82 | assert(v5.apply(o1)); 83 | auto v6=validator( 84 | _[child_word][5]["hello"](exists,true) 85 | ); 86 | assert(!v6.apply(o1)); 87 | 88 | std::cout << "Example 13 done" << std::endl; 89 | return 0; 90 | } 91 | -------------------------------------------------------------------------------- /examples/example14_variadic_property_aggregation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | // sample struct 8 | struct Matrix 9 | { 10 | size_t element(size_t i, size_t j) const noexcept 11 | { 12 | return i+j; 13 | } 14 | 15 | size_t count_i() const noexcept 16 | { 17 | return 1000; 18 | } 19 | 20 | size_t count_j() const noexcept 21 | { 22 | return 100; 23 | } 24 | }; 25 | 26 | // define variadic property 27 | HATN_VALIDATOR_VARIADIC_PROPERTY(element) 28 | 29 | // define "end" properties 30 | HATN_VALIDATOR_PROPERTY(count_i) 31 | HATN_VALIDATOR_PROPERTY(count_j) 32 | 33 | int main() 34 | { 35 | Matrix m1; 36 | 37 | // check if each element is greater than 100 - fails 38 | auto v1=validator( 39 | _[element][varg(ALL,count_i)][varg(ALL,count_j)](gt,100) 40 | ); 41 | assert(!v1.apply(m1)); 42 | 43 | // check if at least one element is greater than 100 - succeeds 44 | auto v2=validator( 45 | _[element][varg(ANY,count_i)][varg(ANY,count_j)](gt,100) 46 | ); 47 | assert(v2.apply(m1)); 48 | 49 | std::cout << "Example 14 done" << std::endl; 50 | return 0; 51 | } 52 | -------------------------------------------------------------------------------- /examples/example15_operator_in.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | int main() 10 | { 11 | // define value for validation 12 | size_t val=90; 13 | 14 | // check if the value is in range 15 | auto v1=validator(in,range({70,80,90,100})); 16 | assert(v1.apply(val)); 17 | 18 | // check if the value is in interval 19 | auto v2=validator(in,interval(80,100)); 20 | assert(v2.apply(val)); 21 | 22 | std::cout << "Example 15 done" << std::endl; 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /examples/example16_operator_negation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | int main() 9 | { 10 | // container to validate 11 | std::map m1={{"key1",100}}; 12 | 13 | // validator with original operator 14 | auto v1=validator( 15 | _["key1"](eq,100) 16 | ); 17 | assert(v1.apply(m1)); 18 | 19 | // validator with negated operator 20 | auto v2=validator( 21 | _["key1"](_n(eq),100) 22 | ); 23 | assert(!v2.apply(m1)); 24 | 25 | std::cout << "Example 16 done" << std::endl; 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /examples/example17_custom_operator.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | // new operator implementation 9 | struct simple_eq_t : public op 10 | { 11 | // comparison operator with two templated arguments 12 | template 13 | constexpr bool operator() (const T1& a, const T2& b) const 14 | { 15 | return a==b; 16 | } 17 | 18 | // direct error description 19 | constexpr static const char* description="must be simply equal to"; 20 | // negated error description 21 | constexpr static const char* n_description="must be not simply equal to"; 22 | }; 23 | // callable object to be used in validators 24 | constexpr simple_eq_t simple_eq{}; 25 | 26 | int main() 27 | { 28 | // define validator with custom operator 29 | auto v1=validator(simple_eq,100); 30 | 31 | error_report err; 32 | 33 | // validate good value 34 | validate(100,v1,err); 35 | assert(!err); 36 | 37 | // validate bad value 38 | validate(90,v1,err); 39 | assert(err); 40 | std::cerr << err.message() << std::endl; 41 | assert(err.message()==std::string("must be simply equal to 100")); 42 | 43 | std::cout << "Example 17 done" << std::endl; 44 | return 0; 45 | } 46 | -------------------------------------------------------------------------------- /examples/example18_move_copy.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | int main () 10 | { 11 | std::string key1{"key1"}; 12 | std::string value1{"value1"}; 13 | // key1 and value1 are passed by reference and must stay valid duiring validator life time 14 | auto v1=validator( 15 | _[key1](eq,value1) 16 | ); 17 | 18 | std::string key2{"key2"}; 19 | std::string value2{"value2"}; 20 | // key2 and value2 are explicitly moved to validator and validator becomes responsible for their contents 21 | auto v2=validator( 22 | _[std::move(key2)](eq,std::move(value2)) 23 | ); 24 | 25 | std::string key3{"key3"}; 26 | std::string value3{"value3"}; 27 | // key3 and value3 are explicitly copied to validator and validator becomes responsible for copies of their contents 28 | auto v3=validator( 29 | _[copy(key3)](eq,copy(value3)) 30 | ); 31 | 32 | // "key4" and "value4" are implicitly moved to validator and validator is responsible for their contents 33 | auto v4=validator( 34 | _["key4"](eq,"value4") 35 | ); 36 | 37 | // apply validators to map 38 | std::map m1{ 39 | {"key1","value1"}, 40 | {"key2","value2"}, 41 | {"key3","value3"}, 42 | {"key4","value4"} 43 | }; 44 | assert(v1.apply(m1)); 45 | assert(v2.apply(m1)); 46 | assert(v3.apply(m1)); 47 | assert(v4.apply(m1)); 48 | 49 | std::cout << "Example 18 done" << std::endl; 50 | return 0; 51 | } 52 | -------------------------------------------------------------------------------- /examples/example19_lazy_operands.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // define sample getter 10 | int sample=100; 11 | auto get_sample=[&sample]() 12 | { 13 | return sample; 14 | }; 15 | 16 | // define validator with lazy operand 17 | auto v1=validator( 18 | eq,lazy(get_sample) 19 | ); 20 | 21 | // define variable 22 | int val=100; 23 | 24 | // validate variable with original sample 25 | assert(v1.apply(val)); 26 | 27 | // update sample and validate variable again 28 | sample=200; 29 | assert(!v1.apply(val)); 30 | 31 | std::cout << "Example 19 done" << std::endl; 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /examples/example20_operand_other_member.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // validator to check if "password" is equal to "check_password" 10 | auto v1=validator( 11 | _["password"](eq,_["check_password"]) 12 | ); 13 | 14 | // map to validate, just for example - NEVER use such passwords! 15 | std::map m1={ 16 | {"password","12345678"}, 17 | {"check_password","12345678"} 18 | }; 19 | 20 | // validate map 21 | assert(v1.apply(m1)); 22 | 23 | std::cout << "Example 20 done" << std::endl; 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /examples/example21_operand_sample_object.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | using namespace HATN_VALIDATOR_NAMESPACE; 6 | 7 | int main() 8 | { 9 | // sample container 10 | std::map sample={ 11 | {"token","12345678"} 12 | }; 13 | 14 | // validator to check if "token" element of object under validation 15 | // is equal to "token" element of the sample 16 | auto v1=validator( 17 | _["token"](eq,_(sample)) 18 | ); 19 | 20 | // map to validate 21 | std::map m1={ 22 | {"token","12345678"} 23 | }; 24 | 25 | // validate map 26 | assert(v1.apply(m1)); 27 | 28 | std::cout << "Example 21 done" << std::endl; 29 | return 0; 30 | } 31 | -------------------------------------------------------------------------------- /examples/example22_element_aggregation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace HATN_VALIDATOR_NAMESPACE; 8 | 9 | int main() 10 | { 11 | std::map m1{ 12 | {"key1","value1"}, 13 | {"key2","value2"}, 14 | {"key3","value3"} 15 | }; 16 | std::map m2{ 17 | {"key1","val1"}, 18 | {"key2","val2"}, 19 | {"key","val3"} 20 | }; 21 | 22 | // validate keys 23 | auto v1=validator( 24 | _[ALL(keys)](gt,"key") 25 | ); 26 | assert(v1.apply(m1)); 27 | assert(!v1.apply(m2)); 28 | 29 | // validate values explicitly 30 | auto v2=validator( 31 | _[ALL(values)](gt,"value") 32 | ); 33 | assert(v2.apply(m1)); 34 | assert(!v2.apply(m2)); 35 | 36 | // va;idate values implicitly 37 | auto v2_1=validator( 38 | _[ALL](gt,"value") 39 | ); 40 | assert(v2_1.apply(m1)); 41 | assert(!v2_1.apply(m2)); 42 | 43 | // validate first elements of iterators 44 | auto v3=validator( 45 | _[ALL(iterators)](first(gt,"key")) 46 | ); 47 | assert(v3.apply(m1)); 48 | assert(!v3.apply(m2)); 49 | 50 | // validate second elements of iterators 51 | auto v4=validator( 52 | _[ALL(iterators)](second(gt,"value")) 53 | ); 54 | assert(v4.apply(m1)); 55 | assert(!v4.apply(m2)); 56 | 57 | std::cout << "Example 22 done" << std::endl; 58 | return 0; 59 | } 60 | -------------------------------------------------------------------------------- /examples/example23_tree_validation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | using namespace HATN_VALIDATOR_NAMESPACE; 9 | 10 | // define tree node 11 | struct TreeNode 12 | { 13 | TreeNode(std::string name) : _name(std::move(name)) 14 | {} 15 | 16 | void add_child(std::shared_ptr child) 17 | { 18 | _children.push_back(std::move(child)); 19 | } 20 | 21 | const TreeNode& child(size_t index) const 22 | { 23 | return *_children.at(index); 24 | } 25 | 26 | auto mutable_child(size_t index) 27 | { 28 | return _children.at(index); 29 | } 30 | 31 | size_t child_count() const noexcept 32 | { 33 | return _children.size(); 34 | } 35 | 36 | std::string name() const 37 | { 38 | return _name; 39 | } 40 | 41 | std::vector> _children; 42 | std::string _name; 43 | }; 44 | 45 | // name proeprty is used to access name of a node 46 | HATN_VALIDATOR_PROPERTY(name) 47 | // child_count property is used to get number of the node's children 48 | HATN_VALIDATOR_PROPERTY(child_count) 49 | // child is a variadic property for accessing a node's child by index 50 | HATN_VALIDATOR_VARIADIC_PROPERTY(child) 51 | 52 | int main() 53 | { 54 | // define tree validator 55 | auto v1=validator( 56 | _[tree(ALL,child,child_count)][name](gte,"Node") 57 | ); 58 | 59 | // tree with one top level node satisfying validation conditions 60 | TreeNode tr1("Node 0"); 61 | assert(v1.apply(tr1)); 62 | 63 | // tree with one top level node not satisfying validation conditions 64 | TreeNode tr2("0"); 65 | assert(!v1.apply(tr2)); 66 | 67 | // populate top node with children 68 | tr1.add_child(std::make_shared("Node 0.0")); 69 | assert(v1.apply(tr1)); 70 | tr1.add_child(std::make_shared("Node 0.1")); 71 | assert(v1.apply(tr1)); 72 | tr1.add_child(std::make_shared("Node 0.2")); 73 | assert(v1.apply(tr1)); 74 | 75 | // populate nested nodes 76 | tr1.mutable_child(0)->add_child(std::make_shared("Node 0.0.0")); 77 | assert(v1.apply(tr1)); 78 | tr1.mutable_child(0)->add_child(std::make_shared("Node 0.0.1")); 79 | assert(v1.apply(tr1)); 80 | tr1.mutable_child(1)->add_child(std::make_shared("Node 0.1.0")); 81 | assert(v1.apply(tr1)); 82 | tr1.mutable_child(2)->add_child(std::make_shared("Node 0.2.0")); 83 | assert(v1.apply(tr1)); 84 | 85 | // validate nested node that doesn't satisfy validation conditions and construct report 86 | std::string rep; 87 | auto ra1=make_reporting_adapter(tr1,rep); 88 | tr1.mutable_child(2)->add_child(std::make_shared("0.2.1")); 89 | assert(!v1.apply(ra1)); 90 | assert(rep==std::string("name of each tree node must be greater than or equal to Node")); 91 | 92 | std::cout << "Example 23 done" << std::endl; 93 | return 0; 94 | } 95 | -------------------------------------------------------------------------------- /examples/example24_partial_validation.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | using namespace HATN_VALIDATOR_NAMESPACE; 11 | 12 | int main() 13 | { 14 | // original validator 15 | auto v1=validator( 16 | _["level1"]["field1"](exists,true), 17 | _["level1"]["field2"](exists,true), 18 | _["level2"]["field3"](exists,true) 19 | ); 20 | 21 | // container to validate 22 | std::map> m1{ 23 | {"level1",{"field1","field2"}}, 24 | {"level2",{"field4"}}, 25 | }; 26 | // wrap container into default adapter 27 | auto a1=make_default_adapter(m1); 28 | 29 | // validation fails with original validator 30 | assert(!v1.apply(a1)); 31 | 32 | // limit validation paths to a single path 33 | auto a2=include_paths(a1, 34 | member_path_list(_["level1"]) 35 | ); 36 | // validation succeeded with partial validation 37 | assert(v1.apply(a2)); 38 | 39 | // exclude failing path from validation 40 | auto a3=exclude_paths(a1, 41 | member_path_list(_["level2"]["field3"]) 42 | ); 43 | // validation succeeded 44 | assert(v1.apply(a3)); 45 | 46 | // include paths for validation and exclude failing sub-path 47 | auto a4=include_and_exclude_paths(a1, 48 | member_path_list(_["level1"],_["level2"]), 49 | member_path_list(_["level2"]["field3"]) 50 | ); 51 | // validation succeeded 52 | assert(v1.apply(a4)); 53 | 54 | std::cout << "Example 24 done" << std::endl; 55 | return 0; 56 | } 57 | -------------------------------------------------------------------------------- /examples/example25_validate_evaluation_result.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | namespace { 9 | // define handler that returns a size of provided string 10 | size_t string_size(const std::string& val) noexcept 11 | { 12 | return val.size(); 13 | } 14 | } 15 | 16 | int main() 17 | { 18 | // create value transforming property 19 | auto transformer=make_value_transformer(string_size,"string size"); 20 | 21 | // value transformer with member notation 22 | auto v1=validator( 23 | _[transformer](gte,5) 24 | ); 25 | // value transformer with property notation 26 | auto v2=validator( 27 | transformer(gte,5) 28 | ); 29 | 30 | // validate string that satisfies validation conditions 31 | std::string s1("Hello world"); 32 | assert(v1.apply(s1)); 33 | assert(v2.apply(s1)); 34 | 35 | // validate string that does not satisfy validation conditions 36 | std::string s2("Hi"); 37 | assert(!v1.apply(s2)); 38 | assert(!v2.apply(s2)); 39 | 40 | std::cout << "Example 25 done" << std::endl; 41 | return 0; 42 | } 43 | -------------------------------------------------------------------------------- /examples/example26_prevalidate_set_member.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | HATN_VALIDATOR_PROPERTY(field1) 9 | 10 | int main() 11 | { 12 | // define validator 13 | auto v=validator( 14 | _["field1"](gte,100) 15 | ); 16 | 17 | std::map m1; 18 | error_report err; 19 | 20 | // set valid value 21 | set_validated(m1,_["field1"],1000,v,err); 22 | assert(!err); // success 23 | assert(m1["field1"]==1000); // was set 24 | 25 | // try to set invalid value 26 | set_validated(m1,_["field1"],10,v,err); 27 | assert(err); // fail 28 | assert(m1["field1"]==1000); // not changed 29 | 30 | std::cout << "Example 26 done" << std::endl; 31 | return 0; 32 | } 33 | -------------------------------------------------------------------------------- /examples/example27_prevalidate_set_custom_property.cpp: -------------------------------------------------------------------------------- 1 | #undef NDEBUG 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | // define structure with member variables and member setter method 9 | struct Foo 10 | { 11 | std::string bar_value; 12 | 13 | uint32_t other_value; 14 | size_t some_size; 15 | 16 | void set_bar_value(std::string val) 17 | { 18 | bar_value=std::move(val); 19 | } 20 | }; 21 | 22 | // define custom properties 23 | HATN_VALIDATOR_PROPERTY(bar_value); 24 | HATN_VALIDATOR_PROPERTY(other_value); 25 | 26 | // template specialization for setting bar_value member of Foo 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | template <> 30 | struct set_member_t 31 | { 32 | template 33 | void operator() ( 34 | ObjectT& obj, 35 | MemberT&&, 36 | ValueT&& val 37 | ) const 38 | { 39 | obj.set_bar_value(std::forward(val)); 40 | } 41 | }; 42 | 43 | HATN_VALIDATOR_NAMESPACE_END 44 | 45 | using namespace HATN_VALIDATOR_NAMESPACE; 46 | 47 | int main() 48 | { 49 | // define validator of custom properties 50 | auto v=validator( 51 | _[bar_value](ilex_ne,"UNKNOWN"), // case insensitive lexicographical not equal 52 | _[other_value](gte,1000) 53 | ); 54 | 55 | Foo foo_instance; 56 | 57 | error_report err; 58 | 59 | // call setter with valid data 60 | set_validated(foo_instance,_[bar_value],"Hello world",v,err); 61 | assert(!err); 62 | 63 | // call setter with invalid data 64 | set_validated(foo_instance,_[bar_value],"unknown",v,err); 65 | assert(err); 66 | if (err) 67 | { 68 | // object's member is not set 69 | std::cerr << err.message() << std::endl; 70 | assert(err.message()==std::string("bar_value must be not equal to UNKNOWN")); 71 | } 72 | 73 | std::cout << "Example 26 done" << std::endl; 74 | return 0; 75 | } 76 | -------------------------------------------------------------------------------- /include/hatn/validator/adapters/adapter_traits_wrapper.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/adapters/adapter_traits_wrapper.hpp 12 | * 13 | * Defines adapter_traits_wrapper. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ADAPTER_TRAITS_WRAPPER_HPP 20 | #define HATN_VALIDATOR_ADAPTER_TRAITS_WRAPPER_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Tag of all adapter traits that wrap other adapter traits. 30 | */ 31 | struct adapter_traits_wrapper_tag{}; 32 | 33 | /** 34 | * @brief Adapter traits used to wrap other adapter traits. 35 | * This traits implement "decorator" design pattern. Consequently, this traits can be used to add additional 36 | * behaviors to original adapters. 37 | */ 38 | template 39 | struct adapter_traits_wrapper : public adapter_traits_wrapper_tag, 40 | public TraitsT::base_tag 41 | { 42 | using expand_aggregation_members=typename TraitsT::expand_aggregation_members; 43 | using filter_if_not_exists=typename TraitsT::filter_if_not_exists; 44 | using base_tag=typename TraitsT::base_tag; 45 | 46 | /** 47 | * @brief Constructor. 48 | * @param traits Original adapter traits. 49 | */ 50 | adapter_traits_wrapper(TraitsT& traits) : _traits(traits) 51 | {} 52 | 53 | /** 54 | * @brief Get original adapter traits. 55 | * @return Original adapter traits. 56 | */ 57 | TraitsT& wrapped() 58 | { 59 | return _traits; 60 | } 61 | 62 | /** 63 | * @brief Get original adapter traits. 64 | * @return Original adapter traits. 65 | */ 66 | const TraitsT& wrapped() const 67 | { 68 | return _traits; 69 | } 70 | 71 | TraitsT& _traits; 72 | }; 73 | 74 | /** 75 | * @brief Implementer of traits_of(). 76 | */ 77 | struct traits_of_impl 78 | { 79 | template 80 | auto operator () (AdapterT&& adapter) const -> decltype(auto) 81 | { 82 | return hana::if_( 83 | std::is_base_of::type>{}, 84 | [](auto&& adapter) -> decltype(auto) 85 | { 86 | return adapter.traits().wrapped(); 87 | }, 88 | [](auto&& adapter) -> decltype(auto) 89 | { 90 | return adapter.traits(); 91 | } 92 | )(std::forward(adapter)); 93 | } 94 | }; 95 | /** 96 | * @brief Get traits of adapter. 97 | * @param adapter Adapter. 98 | * @return Adapter traits or original adapter traits in case this is a wrapping adapter. 99 | */ 100 | constexpr traits_of_impl traits_of{}; 101 | 102 | //------------------------------------------------------------- 103 | 104 | HATN_VALIDATOR_NAMESPACE_END 105 | 106 | #endif // HATN_VALIDATOR_ADAPTER_TRAITS_WRAPPER_HPP 107 | -------------------------------------------------------------------------------- /include/hatn/validator/adapters/failed_members_adapter.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/adapters/failed_members_adapter.hpp 12 | * 13 | * Defines adapter that collects all failed members. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_FAILED_MEMBERS_ADAPTER_HPP 20 | #define HATN_VALIDATOR_FAILED_MEMBERS_ADAPTER_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | * @brief Create adapter that collects all failed members. 32 | * @param obj Object to validate. 33 | * @return Adapter. 34 | * 35 | * The list of failed member names can be accessed via adapter.traits().reporter().failed_members() after validation. 36 | * 37 | * @note Note 1. When validation with this adapter fails then validator.apply() returns either status::ignore or status::success, i.e. its result is useless. 38 | * In order to figure out actual validation result check if the list of failed members is empty. If it is empty then validation succeeded, if it is not empty then validation failed. 39 | * 40 | * @note Note 2. Use with care with validators that check member existence before checking value - if the member does not exist then 41 | * undefined behaviour is possible, e.g. an exception can be thrown or even the application crashes. 42 | * 43 | * @note Note 3. If validator is too complicated, e.g. it includes NOT aggregation or some other deeply nested conditions, 44 | * then failed member collecting might not work properly - some members might be missing while some other members might be excessive. 45 | * 46 | * @note Note 4. This adapter keeps data after validation completes. To reuse it again adapter.reset() must be called before next use. 47 | * 48 | */ 49 | template 50 | auto make_failed_members_adapter(ObjT&& obj) 51 | { 52 | return reporting_adapter(std::forward(obj),failed_members_reporter{}); 53 | } 54 | 55 | //------------------------------------------------------------- 56 | 57 | HATN_VALIDATOR_NAMESPACE_END 58 | 59 | #endif // HATN_VALIDATOR_FAILED_MEMBERS_ADAPTER_HPP 60 | -------------------------------------------------------------------------------- /include/hatn/validator/aggregation/aggregation.ipp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/aggregation/aggregation.ipp 12 | * 13 | * Defines aggregation used for logical operators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATION_IPP 20 | #define HATN_VALIDATOR_AGGREGATION_IPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | 30 | HATN_VALIDATOR_NAMESPACE_BEGIN 31 | 32 | //------------------------------------------------------------- 33 | 34 | /** 35 | * @brief Helper for construction of element aggregation reports. 36 | */ 37 | template > 38 | struct aggregate_report 39 | { 40 | template 41 | static void open(AdapterT1&&, AggregationT&&, MemberT&&) 42 | {} 43 | 44 | template 45 | static void close(AdapterT1&&, status) 46 | {} 47 | }; 48 | 49 | template 50 | struct aggregate_report::type>::value 53 | >> 54 | { 55 | template 56 | static void open(AdapterT1&& adapter, AggregationT&& str, PathT&& path) 57 | { 58 | auto& reporter=traits_of(adapter).reporter(); 59 | hana::eval_if( 60 | hana::is_empty(path), 61 | [&](auto&&) 62 | { 63 | reporter.aggregate_open(str); 64 | }, 65 | [&](auto&& _) 66 | { 67 | reporter.aggregate_open(str,make_member(_(path))); 68 | } 69 | ); 70 | } 71 | 72 | template 73 | static void close(AdapterT1&& adapter, status ret) 74 | { 75 | traits_of(adapter).reporter().aggregate_close(ret); 76 | } 77 | }; 78 | 79 | //------------------------------------------------------------- 80 | 81 | HATN_VALIDATOR_NAMESPACE_END 82 | 83 | #endif // HATN_VALIDATOR_AGGREGATION_IPP 84 | -------------------------------------------------------------------------------- /include/hatn/validator/aggregation/not.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/not.hpp 12 | * 13 | * Defines logical pseudo operator NOT. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_NOT_HPP 20 | #define HATN_VALIDATOR_NOT_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | /** 33 | * @brief Definition of logical pseudo operator NOT. 34 | * @param op Intermediate validator whose result must be negated. 35 | * @return Logical "not" of intermediate validator result. 36 | * 37 | */ 38 | struct not_t 39 | { 40 | template 41 | constexpr auto operator() (Ops&&... ops) const 42 | { 43 | return (*this)(AND(std::forward(ops)...)); 44 | } 45 | 46 | template 47 | constexpr auto operator() (OpT&& op) const 48 | { 49 | return make_validator( 50 | make_aggregation_validator( 51 | detail::logical_not, 52 | std::forward(op) 53 | ) 54 | ); 55 | } 56 | }; 57 | /** 58 | @brief Logical pseudo operator NOT 59 | */ 60 | constexpr not_t NOT{}; 61 | 62 | template 63 | auto validator_t::operator !() 64 | { 65 | return NOT(std::move(*this)); 66 | } 67 | 68 | template 69 | auto validator_with_hint_t::operator !() 70 | { 71 | return NOT(std::move(*this)); 72 | } 73 | 74 | template 75 | auto validator_with_member_t::operator !() 76 | { 77 | return NOT(std::move(*this)); 78 | } 79 | 80 | template 81 | auto base_validator::operator !() 82 | { 83 | return NOT(std::move(*this)); 84 | } 85 | 86 | //------------------------------------------------------------- 87 | 88 | /** 89 | * @brief String descriptions helper for operator NOT. 90 | */ 91 | struct string_not_t : public logical_op 92 | { 93 | constexpr static const aggregation_id id=aggregation_id::NOT; 94 | constexpr static const char* open_token="NOT "; 95 | constexpr static const char* close_token=""; 96 | constexpr static const char* conjunction_token=""; 97 | }; 98 | 99 | /** 100 | @brief Instance of string description helper for operator NOT. 101 | */ 102 | constexpr string_not_t string_not{}; 103 | 104 | //------------------------------------------------------------- 105 | 106 | HATN_VALIDATOR_NAMESPACE_END 107 | 108 | #endif // HATN_VALIDATOR_NOT_HPP 109 | -------------------------------------------------------------------------------- /include/hatn/validator/aggregation/or.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/or.hpp 12 | * 13 | * Defines logical pseudo operator OR. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OR_HPP 20 | #define HATN_VALIDATOR_OR_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | /** 33 | * @brief Logical pseudo operator OR. 34 | * @param xs Intermediate validators whose result must be forwarded to logical OR. 35 | * @return Logical "or" of intermediate validator results. 36 | * 37 | * Can be used both in functioin call notation OR(...) and in infix notation (... ^OR^ ...). 38 | */ 39 | HATN_VALIDATOR_INLINE_LAMBDA auto OR=hana::infix([](auto&& ...xs) -> decltype(auto) 40 | { 41 | return make_validator( 42 | make_aggregation_validator( 43 | detail::aggregate_or, 44 | hana::make_tuple(std::forward(xs)...) 45 | ) 46 | ); 47 | }); 48 | 49 | template 50 | template 51 | auto validator_t::operator || (T&& v) 52 | { 53 | return OR(std::move(*this),std::forward(v)); 54 | } 55 | 56 | template 57 | template 58 | auto validator_with_hint_t::operator || (T&& v) 59 | { 60 | return OR(std::move(*this),std::forward(v)); 61 | } 62 | 63 | template 64 | template 65 | auto validator_with_member_t::operator || (T&& v) 66 | { 67 | return OR(std::move(*this),std::forward(v)); 68 | } 69 | 70 | template 71 | template 72 | auto base_validator::operator || (T&& v) 73 | { 74 | return OR(std::move(*this),std::forward(v)); 75 | } 76 | 77 | //------------------------------------------------------------- 78 | 79 | /** 80 | * @brief String descriptions helper for operator OR. 81 | */ 82 | struct string_or_t : public logical_op 83 | { 84 | constexpr static const aggregation_id id=aggregation_id::OR; 85 | constexpr static const char* open_token="("; 86 | constexpr static const char* close_token=")"; 87 | constexpr static const char* conjunction_token=" OR "; 88 | }; 89 | 90 | /** 91 | @brief Instance of string description helper for operator OR. 92 | */ 93 | constexpr string_or_t string_or{}; 94 | 95 | //------------------------------------------------------------- 96 | 97 | HATN_VALIDATOR_NAMESPACE_END 98 | 99 | #endif // HATN_VALIDATOR_OR_HPP 100 | -------------------------------------------------------------------------------- /include/hatn/validator/aggregation/wrap_heterogeneous_index.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/wrap_heterogeneous_index.hpp 12 | * 13 | * Defines wrapper of heterogeneous index. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_WRAP_HETEROGENEOUS_INDEX_HPP 20 | #define HATN_VALIDATOR_WRAP_HETEROGENEOUS_INDEX_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | /** 28 | * @brief Wrapper of index of element of heterogeneous container for element aggregations. 29 | */ 30 | template 31 | struct wrap_heterogeneous_index_t : public heterogeneous_property_t 32 | { 33 | /** 34 | * @brief Name of index. 35 | */ 36 | constexpr static auto name() 37 | { 38 | return AggregationT::description; 39 | } 40 | 41 | template 42 | constexpr static const char* flag_str(bool, const FormatterT&, bool =false) 43 | { 44 | return nullptr; 45 | } 46 | 47 | constexpr static bool has_flag_str() 48 | { 49 | return false; 50 | } 51 | }; 52 | 53 | /** 54 | * @brief Wrap index of heterogeneous container for element aggregation. 55 | * @param Ti Itegral constant index. 56 | * @param Ta Aggregation. 57 | * @return Wrapped heterogeneous index. 58 | */ 59 | template 60 | constexpr auto wrap_heterogeneous_index(Ti&&, Ta&&) 61 | { 62 | using IndexT=std::decay_t; 63 | return wrap_heterogeneous_index_t< 64 | IndexT::value, 65 | std::decay_t 66 | >{}; 67 | } 68 | 69 | HATN_VALIDATOR_NAMESPACE_END 70 | 71 | #endif // HATN_VALIDATOR_WRAP_HETEROGENEOUS_INDEX_HPP 72 | -------------------------------------------------------------------------------- /include/hatn/validator/apply_generated_paths.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/apply_generated_paths.hpp 12 | * 13 | * Defines "apply_generated_paths". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_APPLY_GENERATED_PATHS_HPP 20 | #define HATN_VALIDATOR_APPLY_GENERATED_PATHS_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief Implementer of apply_generated_paths. 31 | */ 32 | struct apply_generated_paths_impl 33 | { 34 | template 35 | status operator () (UsedPathSizeT&& used_path_size, PathT&& current_path, AdapterT&&, MemberT&& member, HandlerT&& handler) const; 36 | }; 37 | /** 38 | * @brief Apply validation handler to generated member path. 39 | * @param used_path_size Length of already used member's path prefix. 40 | * @param current_path Current path to apply handler to. 41 | * @param adapter Validation adapter. 42 | * @param member Member. 43 | * @param handler Validation handler. 44 | * @return Status of validation. 45 | */ 46 | constexpr apply_generated_paths_impl apply_generated_paths{}; 47 | 48 | //------------------------------------------------------------- 49 | 50 | HATN_VALIDATOR_NAMESPACE_END 51 | 52 | #endif // HATN_VALIDATOR_APPLY_GENERATED_PATHS_HPP 53 | -------------------------------------------------------------------------------- /include/hatn/validator/apply_generated_paths.ipp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/apply_generated_paths.ipp 12 | * 13 | * Defines "apply_generated_paths". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_FILTER_MEMBER_IPP 20 | #define HATN_VALIDATOR_FILTER_MEMBER_IPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | 29 | HATN_VALIDATOR_NAMESPACE_BEGIN 30 | 31 | template 32 | status apply_generated_paths_impl::operator () (UsedPathSizeT&& used_path_size, PathT&& current_path, AdapterT&& adapter, MemberT&& member, HandlerT&& handler) const 33 | { 34 | return hana::eval_if( 35 | hana::greater_equal(used_path_size,hana::size(member.path())), 36 | [&](auto&& _) 37 | { 38 | return generate_paths>(_(used_path_size),_(current_path),_(adapter),_(handler)); 39 | }, 40 | [&](auto&& _) 41 | { 42 | auto&& key=wrap_object_ref(hana::at(_(member).path(),_(used_path_size))); 43 | return generate_paths>( 44 | hana::plus(_(used_path_size),hana::size_c<1>), 45 | hana::append(_(current_path),std::move(key)), 46 | _(adapter), 47 | _(handler) 48 | ); 49 | } 50 | ); 51 | } 52 | 53 | HATN_VALIDATOR_NAMESPACE_END 54 | 55 | #endif // HATN_VALIDATOR_FILTER_MEMBER_HPP 56 | -------------------------------------------------------------------------------- /include/hatn/validator/apply_member_path.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/apply_member_path.hpp 12 | * 13 | * Defines "apply_member_path". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_APPLY_MEMBER_PATH_HPP 20 | #define HATN_VALIDATOR_APPLY_MEMBER_PATH_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief Implementer of apply_member_path. 31 | */ 32 | struct apply_member_path_impl 33 | { 34 | template 35 | status operator () (UsedPathSizeT&& used_path_size, PathT&& current_path, FnT&& fn, AdapterT&& adapter, MemberT&& member) const; 36 | }; 37 | /** 38 | * @brief Apply validation handler to member path. 39 | * @param used_path_size Length of already used member's path prefix. 40 | * @param current_path Current path to apply handler to. 41 | * @param fn Validation handler. 42 | * @param adapter Validation adapter. 43 | * @param member Member. 44 | * @return Status of validation. 45 | * 46 | * Member path might be not the final actual path the validation is applied to. 47 | * If there are aggregations in path then actual paths would be generated and processed in apply_generated_paths(). 48 | */ 49 | constexpr apply_member_path_impl apply_member_path{}; 50 | 51 | 52 | //------------------------------------------------------------- 53 | 54 | HATN_VALIDATOR_NAMESPACE_END 55 | 56 | #endif // HATN_VALIDATOR_APPLY_MEMBER_PATH_HPP 57 | -------------------------------------------------------------------------------- /include/hatn/validator/basic_property.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/basic_property.hpp 12 | * 13 | * Defines basic_property and property_tag. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_BASIC_PROPERTY_HPP 20 | #define HATN_VALIDATOR_BASIC_PROPERTY_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | struct property_tag; 28 | 29 | //------------------------------------------------------------- 30 | 31 | /** 32 | * @brief base struct for properties. 33 | */ 34 | struct basic_property : public adjust_storable_ignore 35 | { 36 | using hana_tag=property_tag; 37 | }; 38 | 39 | 40 | //------------------------------------------------------------- 41 | 42 | HATN_VALIDATOR_NAMESPACE_END 43 | 44 | #endif // HATN_VALIDATOR_BASIC_PROPERTY_HPP 45 | -------------------------------------------------------------------------------- /include/hatn/validator/config.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/config.hpp 12 | * 13 | * Defines configuration macros used throughout the library. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_CONFIG_HPP 20 | #define HATN_VALIDATOR_CONFIG_HPP 21 | 22 | #include 23 | 24 | #define HATN_VALIDATOR_NAMESPACE_BEGIN namespace hatn { namespace vld { 25 | #define HATN_VALIDATOR_NAMESPACE_END }} 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | namespace hana=boost::hana; 30 | 31 | HATN_VALIDATOR_NAMESPACE_END 32 | 33 | #define HATN_VALIDATOR_NAMESPACE hatn::vld 34 | #define HATN_VALIDATOR_USING using namespace hatn::vld; 35 | #define HATN_VALIDATOR_NS vld 36 | 37 | #if __cplusplus >= 201703L 38 | #define HATN_VALIDATOR_INLINE_LAMBDA inline 39 | #else 40 | #define HATN_VALIDATOR_INLINE_LAMBDA static 41 | #endif 42 | 43 | #endif // HATN_VALIDATOR_CONFIG_HPP 44 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/aggregate_all.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/aggregate_all.hpp 12 | * 13 | * Defines ALL aggregation for validating if all elements satisfy validation conditions. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATE_ALL_HPP 20 | #define HATN_VALIDATOR_AGGREGATE_ALL_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | namespace detail 31 | { 32 | 33 | /** 34 | * @brief Aggregation operator for checking if all elements of a container satisfy the condition. 35 | */ 36 | struct aggregate_all_t 37 | { 38 | /** 39 | * @brief Execute validator on container. 40 | * @param a Container to validate or adapter. 41 | * @param op Validator to apply to container's elements. 42 | * @return True if all elements of the container passed the validator. 43 | */ 44 | template 45 | constexpr bool operator ()(T&& a,OpT&& op) const 46 | { 47 | return apply_member(std::forward(a),std::forward(op),make_plain_member(ALL)); 48 | } 49 | 50 | /** 51 | * @brief Execute validator on elements of object's member. 52 | * @param a Object to validate or adapter. 53 | * @param member Member to process with validator, assumed to be a container. 54 | * @param op Validator to apply to container's elements. 55 | * @return True if all elements of the container passed the validator. 56 | */ 57 | template 58 | constexpr bool operator () (T&& a,MemberT&& member,OpT&& op) const 59 | { 60 | return apply_member(std::forward(a),std::forward(op),member[ALL]); 61 | } 62 | }; 63 | 64 | /** 65 | @brief Instance of aggregation operator for checking if all elements of a container satisfy the condition. 66 | */ 67 | constexpr aggregate_all_t aggregate_all{}; 68 | } 69 | 70 | //------------------------------------------------------------- 71 | 72 | HATN_VALIDATOR_NAMESPACE_END 73 | 74 | #endif // HATN_VALIDATOR_AGGREGATE_ALL_HPP 75 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/aggregate_and.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/aggregate_and.hpp 12 | * 13 | * Defines aggregation of intermediate validators or validation operators using logical AND. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATE_AND_HPP 20 | #define HATN_VALIDATOR_AGGREGATE_AND_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | namespace detail 30 | { 31 | 32 | /** 33 | * @brief Aggregation of intermediate validators using logical AND. 34 | */ 35 | struct aggregate_and_t 36 | { 37 | /** 38 | * @brief Execute validators on object and aggregate their results using logical AND. 39 | * @param a Object to validate or adapter. 40 | * @param ops List of intermediate validators or validation operators. 41 | * @return Logical AND of results of intermediate validators. 42 | */ 43 | template 44 | status operator ()(T&& a,OpsT&& ops) const 45 | { 46 | return dispatcher.validate_and(std::forward(a),std::forward(ops)); 47 | } 48 | 49 | /** 50 | * @brief Execute validators on object's member and aggregate their results using logical AND. 51 | * @param a Object to validate or adapter. 52 | * @param member Member to process with validators. 53 | * @param ops List of intermediate validators or validation operators. 54 | * @return Logical AND of results of intermediate validators. 55 | */ 56 | template 57 | status operator () (T&& a,MemberT&& member,OpsT&& ops) const 58 | { 59 | return dispatcher.validate_and(std::forward(a),std::forward(member),std::forward(ops)); 60 | } 61 | }; 62 | /** 63 | @brief Instance of aggregation of intermediate validators using logical AND. 64 | */ 65 | constexpr aggregate_and_t aggregate_and{}; 66 | } 67 | 68 | //------------------------------------------------------------- 69 | 70 | HATN_VALIDATOR_NAMESPACE_END 71 | 72 | #endif // HATN_VALIDATOR_AGGREGATE_AND_HPP 73 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/aggregate_any.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/aggregate_any.hpp 12 | * 13 | * Defines ANY aggregation for validating if any element satisfies validation conditions. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATE_ANY_HPP 20 | #define HATN_VALIDATOR_AGGREGATE_ANY_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | namespace detail 31 | { 32 | 33 | /** 34 | * @brief Aggregation operator for checking if at least one element of a container satisfies the condition. 35 | */ 36 | struct aggregate_any_t 37 | { 38 | /** 39 | * @brief Execute validator on container. 40 | * @param a Container to validate or adapter. 41 | * @param op Validator to apply to container's elements. 42 | * @return True if all elements of the container passed the validator. 43 | */ 44 | template 45 | constexpr bool operator ()(T&& a,OpT&& op) const 46 | { 47 | return apply_member(std::forward(a),std::forward(op),make_plain_member(ANY)); 48 | } 49 | 50 | /** 51 | * @brief Execute validator on elements of object's member. 52 | * @param a Object to validate or adapter. 53 | * @param member Member to process with validator, assumed to be a container. 54 | * @param op Validator to apply to container's elements. 55 | * @return True if all elements of the container passed the validator. 56 | */ 57 | template 58 | constexpr bool operator () (T&& a,MemberT&& member,OpT&& op) const 59 | { 60 | return apply_member(std::forward(a),std::forward(op),member[ANY]); 61 | } 62 | }; 63 | 64 | /** 65 | * @brief Instance of aggregation operator for checking if at least one element of a container satisfies the condition. 66 | */ 67 | constexpr aggregate_any_t aggregate_any{}; 68 | } 69 | 70 | //------------------------------------------------------------- 71 | 72 | HATN_VALIDATOR_NAMESPACE_END 73 | 74 | #endif // HATN_VALIDATOR_AGGREGATE_ANY_HPP 75 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/aggregate_or.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/aggregate_or.hpp 12 | * 13 | * Defines aggregation of intermediate validators or validation operators using logical AND. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATE_OR_HPP 20 | #define HATN_VALIDATOR_AGGREGATE_OR_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | namespace detail 30 | { 31 | /** 32 | * @brief Aggregation of intermediate validators using logical OR. 33 | */ 34 | struct aggregate_or_t 35 | { 36 | /** 37 | * @brief Execute validators on object and aggregate their results using logical OR. 38 | * @param a Object to validate or adapter. 39 | * @param ops List of intermediate validators or validation operators. 40 | * @return Logical OR of results of intermediate validators. 41 | */ 42 | template 43 | status operator ()(T&& a,OpsT&& ops) const 44 | { 45 | return dispatcher.validate_or(std::forward(a),std::forward(ops)); 46 | } 47 | 48 | /** 49 | * @brief Execute validators on object's member and aggregate their results using logical OR. 50 | * @param a Object to validate or adapter. 51 | * @param member Member to process with validators. 52 | * @param ops List of intermediate validators or validation operators. 53 | * @return Logical OR of results of intermediate validators. 54 | */ 55 | template 56 | status operator () (T&& a,MemberT&& member,OpsT&& ops) const 57 | { 58 | return dispatcher.validate_or(std::forward(a),std::forward(member),std::forward(ops)); 59 | } 60 | }; 61 | 62 | /** 63 | * @brief Instance of aggregation of intermediate validators using logical OR. 64 | */ 65 | constexpr aggregate_or_t aggregate_or{}; 66 | } 67 | 68 | //------------------------------------------------------------- 69 | 70 | HATN_VALIDATOR_NAMESPACE_END 71 | 72 | #endif // HATN_VALIDATOR_AGGREGATE_OR_HPP 73 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/has_property.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/has_property.hpp 12 | * 13 | * Defines implementation of checking if object has a property. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_HAS_PROPERTY_HPP 20 | #define HATN_VALIDATOR_HAS_PROPERTY_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | struct property_tag 30 | { 31 | bool operator ==(const property_tag&) const 32 | { 33 | return true; 34 | } 35 | bool operator !=(const property_tag&) const 36 | { 37 | return false; 38 | } 39 | }; 40 | 41 | //------------------------------------------------------------- 42 | 43 | namespace detail 44 | { 45 | 46 | /** 47 | * @brief Default hepler for probing property existance. 48 | */ 49 | template > 50 | struct has_property_t 51 | { 52 | }; 53 | 54 | /** 55 | * @brief Hepler for probing property existance when object has a property. 56 | */ 57 | template 58 | struct has_property_t>> 59 | { 60 | constexpr bool operator() () const 61 | { 62 | return std::decay_t::template has>(); 63 | } 64 | }; 65 | 66 | /** 67 | * @brief Hepler for probing property existance when object does not have a property. 68 | */ 69 | template 70 | struct has_property_t>> 71 | { 72 | constexpr bool operator() () const 73 | { 74 | return false; 75 | } 76 | }; 77 | 78 | } 79 | 80 | //------------------------------------------------------------- 81 | 82 | HATN_VALIDATOR_NAMESPACE_END 83 | 84 | #endif // HATN_VALIDATOR_HAS_PROPERTY_HPP 85 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/hint_helper.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/hint_helper.hpp 12 | * 13 | * Defines helpers to invoke hint methods. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_HINT_HELPER_HPP 20 | #define HATN_VALIDATOR_HINT_HELPER_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | namespace detail 28 | { 29 | 30 | //------------------------------------------------------------- 31 | 32 | /** 33 | * @brief Default helper to invoke hint_before() method. 34 | */ 35 | template 36 | struct hint_before_t 37 | { 38 | template 39 | status operator() (Args&&...) const 40 | { 41 | return status(); 42 | } 43 | }; 44 | 45 | /** 46 | * @brief Helper to invoke hint_before() method. 47 | */ 48 | template 49 | struct hint_before_t>().hint_before(std::declval>())) 51 | > 52 | { 53 | template 54 | status operator() (T1&& v, T2&& x) const 55 | { 56 | return v.hint_before(std::forward(x)); 57 | } 58 | }; 59 | 60 | /** 61 | * @brief Instance of helper to invoke hint_before() method. 62 | */ 63 | template 64 | constexpr hint_before_t hint_before{}; 65 | 66 | /** 67 | * @brief Default helper to invoke hint_after() method. 68 | */ 69 | template 70 | struct hint_after_t 71 | { 72 | template 73 | status operator() (T1&&, status validation_status, T2&&) const 74 | { 75 | return validation_status; 76 | } 77 | }; 78 | 79 | /** 80 | * @brief Helper to invoke hint_after() method. 81 | */ 82 | template 83 | struct hint_after_t>().hint_after(std::declval(),std::declval>())) 85 | > 86 | { 87 | template 88 | status operator() (T1&& v, status validation_status, T2&& x) const 89 | { 90 | return v.hint_after(validation_status,std::forward(x)); 91 | } 92 | }; 93 | 94 | /** 95 | * @brief Instance of helper to invoke hint_after() method. 96 | */ 97 | template 98 | constexpr hint_after_t hint_after{}; 99 | 100 | //------------------------------------------------------------- 101 | 102 | } 103 | 104 | HATN_VALIDATOR_NAMESPACE_END 105 | 106 | #endif // HATN_VALIDATOR_HINT_HELPER_HPP 107 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/logical_not.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/logical_not.hpp 12 | * 13 | * Defines negation of intermediate validator or validation operators using logical NOT. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_LOGICAL_NOT_HPP 20 | #define HATN_VALIDATOR_LOGICAL_NOT_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | namespace detail 30 | { 31 | 32 | /** 33 | * @brief Helper for negation of intermediate validators using logical NOT. 34 | */ 35 | struct logical_not_t 36 | { 37 | /** 38 | * @brief Execute validator on object and negate its results using logical NOT. 39 | * @param a Object to validate or adapter. 40 | * @param op Intermediate validator or validation operator. 41 | * @return Logical NOT of result of intermediate validator. 42 | */ 43 | template 44 | status operator ()(T&& a,OpT&& op) const 45 | { 46 | return dispatcher.validate_not(std::forward(a),std::forward(op)); 47 | } 48 | 49 | /** 50 | * @brief Execute validator on object's member and negate its result using logical NOT. 51 | * @param a Object to validate or adapter. 52 | * @param member Member to process with validator. 53 | * @param op Intermediate validator or validation operator. 54 | * @return Logical NOT of result of intermediate validator. 55 | */ 56 | template 57 | status operator () (T&& a,MemberT&& member,OpT&& op) const 58 | { 59 | return dispatcher.validate_not(std::forward(a),std::forward(member),std::forward(op)); 60 | } 61 | }; 62 | 63 | /** 64 | * @brief Instance of callable helper for negation of intermediate validators using logical NOT. 65 | */ 66 | constexpr logical_not_t logical_not{}; 67 | } 68 | 69 | //------------------------------------------------------------- 70 | 71 | HATN_VALIDATOR_NAMESPACE_END 72 | 73 | #endif // HATN_VALIDATOR_LOGICAL_NOT_HPP 74 | -------------------------------------------------------------------------------- /include/hatn/validator/detail/member_helper.ipp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/detail/member_helper.ipp 12 | * 13 | * Defines helpers to invoke member methods. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MEMBER_HELPER_IPP 20 | #define HATN_VALIDATOR_MEMBER_HELPER_IPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | namespace detail 29 | { 30 | 31 | template 32 | template 33 | auto member_helper_2args_t>::value>>::operator () 34 | ( 35 | MemberT&& member, 36 | T1&& name, 37 | T2&& grammar_category 38 | ) const 39 | { 40 | return make_member_with_name(std::forward(member),concrete_phrase(std::forward(name),std::forward(grammar_category))); 41 | } 42 | 43 | template 44 | template 45 | auto member_helper_t::operator () 46 | ( 47 | MemberT&& member, 48 | Args&&... args 49 | ) const 50 | { 51 | return make_member_with_name(std::forward(member),concrete_phrase(std::forward(args)...)); 52 | } 53 | 54 | } 55 | 56 | HATN_VALIDATOR_NAMESPACE_END 57 | 58 | #endif // HATN_VALIDATOR_MEMBER_HELPER_IPP 59 | -------------------------------------------------------------------------------- /include/hatn/validator/extract.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/extract.hpp 12 | * 13 | * Defines method to extract value from operand. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_EXTRACT_HPP 20 | #define HATN_VALIDATOR_EXTRACT_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | @brief Extract value from argument. 32 | @param v Argument can be plain value or lazy handler. 33 | @return Either input argument or result of handler evaluation if input is a lazy handler. 34 | */ 35 | template 36 | auto extract(Tv&& v) -> decltype(auto) 37 | { 38 | return hana::if_(hana::is_a, 39 | [](auto&& x) -> decltype(auto) { return extract_operand(x()); }, 40 | [](auto&& x) -> decltype(auto) { return extract_operand(std::forward(x)); } 41 | )(std::forward(v)); 42 | } 43 | 44 | //------------------------------------------------------------- 45 | 46 | HATN_VALIDATOR_NAMESPACE_END 47 | 48 | #endif // HATN_VALIDATOR_EXTRACT_HPP 49 | -------------------------------------------------------------------------------- /include/hatn/validator/generate_paths.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/generate_paths.hpp 12 | * 13 | * Defines "generate_paths". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_GENERATE_PATHS_HPP 20 | #define HATN_VALIDATOR_GENERATE_PATHS_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief Helper for generating member paths. 31 | */ 32 | template > 33 | struct generate_paths_t 34 | { 35 | template 36 | status operator () (UsedPathSizeT&& used_path_size, PathT&& path, AdapterT&& adapter, HandlerT&& handler) const 37 | { 38 | std::ignore=used_path_size; 39 | return handler(std::forward(adapter),std::forward(path),hana::size(path)); 40 | } 41 | }; 42 | /** 43 | * @brief Generate paths from original member's path. 44 | * @param used_path_size Length of already used member's path prefix. 45 | * @param path Previous/original path. 46 | * @param adapter Validation adapter. 47 | * @param handler Validation handler to apply to member with generated path. 48 | * @return Validation status. 49 | * 50 | * Paths can be generated in case of element aggregations and trees. 51 | */ 52 | template 53 | constexpr generate_paths_t generate_paths{}; 54 | 55 | //------------------------------------------------------------- 56 | 57 | HATN_VALIDATOR_NAMESPACE_END 58 | 59 | #endif // HATN_VALIDATOR_GENERATE_PATHS_HPP 60 | -------------------------------------------------------------------------------- /include/hatn/validator/get.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/get.hpp 12 | * 13 | * Defines function for getting member from object. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_GET_HPP 20 | #define HATN_VALIDATOR_GET_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | /** 30 | @brief Get member/element from object. 31 | @param v Object. 32 | @param k Key of the member/element. 33 | @return Either reference to member's value or rvalue that was returned by property. It depends on the object and member implementation. 34 | 35 | If member can not be found by the key then behaviour depends on the object and member implementation, 36 | usually a kind of out_of_range exception will be thrown or some default value will be returned. 37 | */ 38 | template 39 | auto get(Tv&& v, Tk&& k) -> decltype(auto) 40 | { 41 | return detail::get_impl(v))),decltype(unwrap_object(std::forward(k)))> 42 | ( 43 | as_reference(std::forward(v)), 44 | unwrap_object(std::forward(k)) 45 | ) 46 | ; 47 | } 48 | 49 | HATN_VALIDATOR_NAMESPACE_END 50 | 51 | #endif // HATN_VALIDATOR_GET_HPP 52 | -------------------------------------------------------------------------------- /include/hatn/validator/get_member.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/get_member.hpp 12 | * 13 | * Defines extractor of object's member. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_GET_MEMBER_HPP 20 | #define HATN_VALIDATOR_GET_MEMBER_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | //------------------------------------------------------------- 30 | 31 | struct get_member_impl 32 | { 33 | template 34 | auto operator () (Tv&& v, Tpath&& path) const -> decltype(auto) 35 | { 36 | return hana::if_( 37 | hana_tuple_empty{}, 38 | [](auto&& v, auto&&) -> decltype(auto) 39 | { 40 | // empty path means object itself 41 | return hana::id(std::forward(v)); 42 | }, 43 | [](auto&& v, auto&& path) -> decltype(auto) 44 | { 45 | return hana::fold(std::forward(path),std::forward(v), 46 | [](auto&& field, auto&& key) -> decltype(auto) 47 | { 48 | return get(std::forward(field),std::forward(key)); 49 | } 50 | ); 51 | } 52 | )(std::forward(v),std::forward(path)); 53 | } 54 | }; 55 | constexpr get_member_impl get_member_inst{}; 56 | 57 | /** 58 | @brief Extract nested member from object. 59 | @param Top level object. 60 | @param Path to the member to extract. 61 | @return Extracted member. 62 | 63 | In most cases a reference will be returned except for the cases of properties that return rvalues, e.g. size() or empty(). 64 | */ 65 | struct get_member_as_reference_impl 66 | { 67 | template 68 | auto operator () (Tv&& v, Tpath&& path) const -> decltype(auto) 69 | { 70 | return as_reference(get_member_inst(std::forward(v),std::forward(path))); 71 | } 72 | }; 73 | constexpr get_member_as_reference_impl get_member{}; 74 | 75 | //------------------------------------------------------------- 76 | 77 | HATN_VALIDATOR_NAMESPACE_END 78 | 79 | #endif // HATN_VALIDATOR_GET_MEMBER_HPP 80 | -------------------------------------------------------------------------------- /include/hatn/validator/headeronly.cfg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/evgeniums/cpp-validator/c98bbd278800f6e91eee9356cfb5926a9bd6b1b4/include/hatn/validator/headeronly.cfg -------------------------------------------------------------------------------- /include/hatn/validator/ignore_compiler_warnings.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/ignore_compiler_warnings.hpp 12 | * 13 | * Defines macros used to ignore some false or unimportant compiler warnings. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_IGNORE_COMPILER_WARNINGS_HPP 20 | #define HATN_VALIDATOR_IGNORE_COMPILER_WARNINGS_HPP 21 | 22 | #ifndef HATN_IGNORE_MAYBE_UNINITIALIZED_BEGIN 23 | 24 | #if __GNUC__ 25 | #if defined(__has_warning) 26 | #if __has_warning("-Wmaybe-uninitialized") 27 | #define HATN_IGNORE_MAYBE_UNINITIALIZED 28 | #endif 29 | #else 30 | #define HATN_IGNORE_MAYBE_UNINITIALIZED 31 | #endif 32 | #endif // __GNUC__ 33 | 34 | #ifdef HATN_IGNORE_MAYBE_UNINITIALIZED 35 | #define HATN_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ 36 | _Pragma("GCC diagnostic push") \ 37 | _Pragma("GCC diagnostic ignored \"-Wmaybe-uninitialized\"") 38 | #define HATN_IGNORE_MAYBE_UNINITIALIZED_END \ 39 | _Pragma("GCC diagnostic pop") 40 | #else 41 | #define HATN_IGNORE_MAYBE_UNINITIALIZED_BEGIN 42 | #define HATN_IGNORE_MAYBE_UNINITIALIZED_END 43 | #endif // HATN_IGNORE_MAYBE_UNINITIALIZED 44 | 45 | #endif // HATN_IGNORE_MAYBE_UNINITIALIZED_BEGIN 46 | 47 | #ifndef HATN_IGNORE_PARENTHESES_BEGIN 48 | 49 | #if __GNUC__ 50 | #if defined(__has_warning) 51 | #if __has_warning("-Wparentheses") 52 | #define HATN_IGNORE_PARENTHESES 53 | #endif 54 | #else 55 | #define HATN_IGNORE_PARENTHESES 56 | #endif 57 | #endif // __GNUC__ 58 | 59 | #ifdef HATN_IGNORE_PARENTHESES 60 | #define HATN_IGNORE_PARENTHESES_BEGIN \ 61 | _Pragma("GCC diagnostic push") \ 62 | _Pragma("GCC diagnostic ignored \"-Wparentheses\"") 63 | #define HATN_IGNORE_PARENTHESES_END \ 64 | _Pragma("GCC diagnostic pop") 65 | #else 66 | #define HATN_IGNORE_PARENTHESES_BEGIN 67 | #define HATN_IGNORE_PARENTHESES_END 68 | #endif // HATN_IGNORE_PARENTHESES 69 | 70 | #endif // HATN_IGNORE_PARENTHESES_BEGIN 71 | 72 | 73 | #endif // HATN_VALIDATOR_IGNORE_COMPILER_WARNINGS_HPP 74 | -------------------------------------------------------------------------------- /include/hatn/validator/lazy.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/lazy.hpp 12 | * 13 | * Defines wrapper for deferred invokation of a handler. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_LAZY_HPP 20 | #define HATN_VALIDATOR_LAZY_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | struct lazy_tag; 29 | 30 | /** 31 | * @brief Lazy invokation handler. 32 | */ 33 | template 34 | struct lazy_t 35 | { 36 | using hana_tag=lazy_tag; 37 | T fn; 38 | 39 | auto operator()() const -> decltype(fn()) 40 | { 41 | return fn(); 42 | } 43 | }; 44 | 45 | /** 46 | @brief Construct handler for deferred invokation. 47 | @param fn Handler that will be invoked later on demand. 48 | */ 49 | template 50 | auto lazy(T&& fn) -> decltype(auto) 51 | { 52 | return lazy_t{std::forward(fn)}; 53 | } 54 | 55 | //------------------------------------------------------------- 56 | 57 | HATN_VALIDATOR_NAMESPACE_END 58 | 59 | #endif // HATN_VALIDATOR_LAZY_HPP 60 | -------------------------------------------------------------------------------- /include/hatn/validator/make_member.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/make_member.hpp 12 | * 13 | * Defines helpers for member creation. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MAKE_MEMBER_HPP 20 | #define HATN_VALIDATOR_MAKE_MEMBER_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | /** 31 | * @brief Create plain member with one key in path. 32 | * @param key Member's key. 33 | * @return Created member. 34 | */ 35 | template 36 | constexpr auto make_plain_member(T&& key) 37 | { 38 | using type=typename adjust_storable_type::type; 39 | return member{type(std::forward(key))}; 40 | } 41 | 42 | template 43 | constexpr auto make_typed_member(T&& key) 44 | { 45 | return member>{std::forward(key)}; 46 | } 47 | 48 | /** 49 | * @brief Make member from path. 50 | * @param path Member's path. 51 | * @return Created member. 52 | */ 53 | template 54 | auto make_member(Ts&& path) 55 | { 56 | static_assert(std::tuple_size::value!=0,"Path can not be empty"); 57 | 58 | return hana::fold( 59 | hana::drop_front(path), 60 | make_plain_member(std::move(hana::front(path))), 61 | [](auto&& parent_member, auto&& next_key) 62 | { 63 | return parent_member[std::forward(next_key)]; 64 | } 65 | ); 66 | } 67 | 68 | /** 69 | * @brief Make member from keys. 70 | * @param keys Keys of the nested path. 71 | */ 72 | template 73 | auto path(Ts&& ...keys) 74 | { 75 | return make_member(hana::make_tuple(std::forward(keys)...)); 76 | } 77 | 78 | /** 79 | * @brief Make new member inherting given member. 80 | * @param path Path of new member. 81 | * @param member Member to inherit from. 82 | * @return New member. 83 | * 84 | * New member uses name() of original member if applicable. 85 | */ 86 | template 87 | auto inherit_member(Ts&& path, T&& member) 88 | { 89 | return hana::eval_if( 90 | std::is_base_of>{}, 91 | [&](auto&& _) 92 | { 93 | return make_member_with_name(make_member(_(path)),_(member).name()); 94 | }, 95 | [&](auto&& _) 96 | { 97 | return make_member(_(path)); 98 | } 99 | ); 100 | }; 101 | 102 | //------------------------------------------------------------- 103 | 104 | HATN_VALIDATOR_NAMESPACE_END 105 | 106 | #endif // HATN_VALIDATOR_MAKE_MEMBER_HPP 107 | -------------------------------------------------------------------------------- /include/hatn/validator/make_validator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/make_validator.hpp 12 | * 13 | * Defines creator of validator instances. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MAKE_HPP 20 | #define HATN_VALIDATOR_MAKE_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | @brief Create validator instance. 31 | @param fn Validation handler that will be embedded into validator instance. 32 | */ 33 | template 34 | auto make_validator(T fn) 35 | { 36 | auto exists_params=content_of_check_exists(fn); 37 | return validator_t< 38 | T, 39 | std::decay_t 40 | >( 41 | std::move(fn), 42 | exists_params.first, 43 | exists_params.second 44 | ); 45 | } 46 | 47 | /** 48 | @brief Create member validator instance. 49 | @param fn Validation handler that will be embedded into validator instance. 50 | */ 51 | template 52 | auto make_member_validator(MemberT member, ValidatorT&& v) 53 | { 54 | auto exists_params=content_of_check_exists(v); 55 | return validator_with_member_t< 56 | std::decay_t, 57 | std::decay_t, 58 | std::decay_t 59 | >( 60 | std::forward(member), 61 | std::forward(v), 62 | exists_params.first, 63 | exists_params.second 64 | ); 65 | } 66 | 67 | /** 68 | @brief Create validator instance on heap. 69 | @param fn Validation handler that will be embedded into validator instance. 70 | */ 71 | template 72 | auto make_validator_on_heap(T fn) 73 | { 74 | auto exists_params=content_of_check_exists(fn); 75 | return new validator_t< 76 | decltype(fn), 77 | std::decay_t 78 | >( 79 | std::move(fn), 80 | exists_params.first, 81 | exists_params.second 82 | ); 83 | } 84 | 85 | //------------------------------------------------------------- 86 | 87 | HATN_VALIDATOR_NAMESPACE_END 88 | 89 | #endif // HATN_VALIDATOR_MAKE_HPP 90 | -------------------------------------------------------------------------------- /include/hatn/validator/member_property.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/member_property.hpp 12 | * 13 | * Defines pair of a member with the member's property. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MEMBER_PROPERTY_HPP 20 | #define HATN_VALIDATOR_MEMBER_PROPERTY_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | struct member_property_tag; 28 | 29 | /** 30 | * @brief Pair of a member and the member's property. 31 | */ 32 | template 33 | struct member_property 34 | { 35 | using hana_tag=member_property_tag; 36 | 37 | using member_type=MemberT; 38 | using property_type=PropT; 39 | 40 | MemberT member; 41 | PropT property; 42 | }; 43 | 44 | /** 45 | @brief Make pair of a member and the member's property. 46 | @param b ID to wrap into member operand. 47 | @return Pair of a member and the member's property. 48 | */ 49 | template 50 | auto make_member_property(MemberT&& member, PropT&& prop) 51 | { 52 | return member_property{std::forward(member),std::forward(prop)}; 53 | } 54 | 55 | //------------------------------------------------------------- 56 | 57 | HATN_VALIDATOR_NAMESPACE_END 58 | 59 | #endif // HATN_VALIDATOR_MEMBER_PROPERTY_HPP 60 | -------------------------------------------------------------------------------- /include/hatn/validator/member_with_name.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/member_with_name.hpp 12 | * 13 | * Defines member_with_name. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MEMBER_WITH_NAME_HPP 20 | #define HATN_VALIDATOR_MEMBER_WITH_NAME_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | struct member_with_name_tag{}; 28 | 29 | /** 30 | * @brief Member with excplicit name. 31 | */ 32 | template 33 | struct member_with_name : public member, 34 | public member_with_name_tag 35 | { 36 | using base_type=member; 37 | 38 | /** 39 | * @brief Constructor with name. 40 | * @param path Member's path. 41 | * @name name member's name. 42 | */ 43 | template 44 | member_with_name(typename base_type::path_type path, 45 | Tt1&& name) 46 | : base_type(std::move(path)), 47 | _name(std::forward(name)) 48 | {} 49 | 50 | /** 51 | * @brief Get member's name. 52 | * @return Name. 53 | */ 54 | auto name() const -> decltype(auto) 55 | { 56 | return _name; 57 | } 58 | 59 | /** 60 | * @brief member_with_name has explicit name. 61 | */ 62 | constexpr static bool has_name = true; 63 | 64 | /** 65 | * @brief Bind compound validator to current member. 66 | * @param v Prepared partial validator. 67 | * @return Prepared partial validator bound to current member. 68 | */ 69 | template 70 | constexpr auto operator () (Tt1&& v) const -> decltype(auto) 71 | { 72 | return make_member_validator(*this,std::forward(v)); 73 | } 74 | 75 | /** 76 | * @brief Bind plain operator to current member. 77 | * @param op Operator. 78 | * @param b Argument to forward to operator. 79 | * @return Prepared partial validator of "value" property bound to current member. 80 | */ 81 | template 82 | constexpr auto operator () (OpT&& op, Tt1&& b) const -> decltype(auto) 83 | { 84 | return (*this)(value(std::forward(op),std::forward(b))); 85 | } 86 | 87 | T1 _name; 88 | }; 89 | 90 | /** 91 | * @brief Create a member with name from basic member. 92 | * @param member Basic member. 93 | * @param name Member name. 94 | * @return Basic name wrapped with name into member with name. 95 | */ 96 | template 97 | auto make_member_with_name(MemberT&& member, T&& name) 98 | { 99 | return member.template create_derived(std::forward(name),std::move(member._path)); 100 | } 101 | 102 | //------------------------------------------------------------- 103 | 104 | HATN_VALIDATOR_NAMESPACE_END 105 | 106 | #endif // HATN_VALIDATOR_MEMBER_WITH_NAME_HPP 107 | -------------------------------------------------------------------------------- /include/hatn/validator/operand.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operand.hpp 12 | * 13 | * Defines operand wrapper. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OPERAND_HPP 20 | #define HATN_VALIDATOR_OPERAND_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | struct master_sample_tag; 33 | struct operand_tag; 34 | 35 | /** 36 | * @brief Operand wrapper. 37 | * 38 | * Operand wrapper can be used to customize formatting of operand value. 39 | */ 40 | template 41 | class operand : public object_wrapper 42 | { 43 | public: 44 | 45 | using hana_tag=operand_tag; 46 | constexpr static const bool is_master_sample=hana::is_a; 47 | 48 | /** 49 | * @brief Constructor. 50 | * @param val Operand's value. 51 | * @param description String to use in report formatting to represent the operand. 52 | */ 53 | operand( 54 | T&& val, 55 | std::string description=std::string() 56 | ) : object_wrapper(std::forward(val)), 57 | _description(std::move(description)) 58 | {} 59 | 60 | /** 61 | * @brief Operator of conversion to std::string. 62 | */ 63 | operator std::string() const 64 | { 65 | return _description; 66 | } 67 | 68 | private: 69 | 70 | concrete_phrase _description; 71 | }; 72 | 73 | /** 74 | @brief Extract value from operand. 75 | @param v Input. 76 | @return Either v as is or v.get() if input is of operand_tag. 77 | */ 78 | template 79 | auto extract_operand(Tv&& v) ->decltype(auto) 80 | { 81 | return hana::if_(hana::is_a, 82 | [](auto&& x) -> decltype(auto) { return x.get(); }, 83 | [](auto&& x) -> decltype(auto) { return hana::id(std::forward(x)); } 84 | )(std::forward(v)); 85 | } 86 | 87 | //------------------------------------------------------------- 88 | 89 | HATN_VALIDATOR_NAMESPACE_END 90 | 91 | #endif // HATN_VALIDATOR_OPERAND_HPP 92 | -------------------------------------------------------------------------------- /include/hatn/validator/operators.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators.hpp 12 | * 13 | * Includes headers with operators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OPERATORS_HPP 20 | #define HATN_VALIDATOR_OPERATORS_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #include 32 | #include 33 | #include 34 | 35 | HATN_VALIDATOR_NAMESPACE_BEGIN 36 | 37 | //------------------------------------------------------------- 38 | 39 | //------------------------------------------------------------- 40 | 41 | HATN_VALIDATOR_NAMESPACE_END 42 | 43 | #endif // HATN_VALIDATOR_OPERATORS_HPP 44 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/contains.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/contains.hpp 12 | * 13 | * Defines operator "contains". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_CONTAINS_HPP 20 | #define HATN_VALIDATOR_CONTAINS_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | //------------------------------------------------------------- 30 | 31 | /** 32 | * @brief Definition of operator "contains" for checking if object contains a member. 33 | */ 34 | struct contains_t : public op 35 | { 36 | constexpr static const char* description="must contain"; 37 | constexpr static const char* n_description="must not contain"; 38 | 39 | template 40 | constexpr bool operator() (const T1& a, const T2& b) const 41 | { 42 | return check_contains(a,b); 43 | } 44 | }; 45 | 46 | /** 47 | @brief Operator for checking if object contains a member. 48 | */ 49 | constexpr contains_t contains{}; 50 | 51 | //------------------------------------------------------------- 52 | 53 | HATN_VALIDATOR_NAMESPACE_END 54 | 55 | #endif // HATN_VALIDATOR_CONTAINS_HPP 56 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/logical.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators.hpp 12 | * 13 | * Includes all headers with logical operators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OPERATORS_HPP 20 | #define HATN_VALIDATOR_OPERATORS_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | //------------------------------------------------------------- 31 | 32 | HATN_VALIDATOR_NAMESPACE_END 33 | 34 | #endif // HATN_VALIDATOR_OPERATORS_HPP 35 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/number_patterns.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/number_patterns.hpp 12 | * 13 | * Defines operator to validate some number patterns in strings. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_NUMBER_PATTERNS_HPP 20 | #define HATN_VALIDATOR_NUMBER_PATTERNS_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | namespace detail 31 | { 32 | // from https://stackoverflow.com/a/2845275 33 | inline bool is_integer(const std::string& s) 34 | { 35 | if(s.empty() || ((!isdigit(s[0])) && (s[0] != '-') && (s[0] != '+'))) return false; 36 | 37 | char * p; 38 | strtol(s.c_str(), &p, 10); 39 | 40 | return (*p == 0); 41 | } 42 | } 43 | 44 | /** 45 | * @brief Definition of operator "must be integer". 46 | */ 47 | struct str_int_t : public op_report_without_operand 48 | { 49 | constexpr static const char* description="must be integer"; 50 | constexpr static const char* n_description="must not be integer"; 51 | 52 | template 53 | bool operator() (const T1& a, const T2& b) const 54 | { 55 | return detail::is_integer(a)==b; 56 | } 57 | }; 58 | 59 | /** 60 | @brief Operator "must be integer". 61 | */ 62 | constexpr str_int_t str_int{}; 63 | 64 | 65 | /** 66 | * @brief Definition of operator "must be a floating point number". 67 | */ 68 | struct str_float_t : public op_report_without_operand 69 | { 70 | constexpr static const char* description="must be a floating point number"; 71 | constexpr static const char* n_description="must be not a floating point number"; 72 | 73 | template 74 | bool operator() (const T1& a, const T2& b) const 75 | { 76 | static const std::regex e("[-+]?[0-9]*\\.?[0-9]+([eE][-+]?[0-9]+)?"); 77 | return regex_match(a,e)==b; 78 | } 79 | }; 80 | 81 | /** 82 | @brief Operator "must be a floating point number". 83 | */ 84 | constexpr str_float_t str_float{}; 85 | 86 | //------------------------------------------------------------- 87 | 88 | HATN_VALIDATOR_NAMESPACE_END 89 | 90 | #endif // HATN_VALIDATOR_NUMBER_PATTERNS_HPP 91 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/op_report_without_operand.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/op_report_without_operand.hpp 12 | * 13 | * Defines base class for operators that swallow operands in reports. 14 | */ 15 | 16 | /****************************************************************************/ 17 | 18 | #ifndef HATN_VALIDATOR_OP_REPORT_WITHOUT_OPERAND_HPP 19 | #define HATN_VALIDATOR_OP_REPORT_WITHOUT_OPERAND_HPP 20 | 21 | #include 22 | 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | * @brief Base class for operators that swallow operands in reports. 32 | */ 33 | struct op_report_without_operand_t : public adjust_storable_ignore 34 | { 35 | using hana_tag=operator_tag; 36 | }; 37 | 38 | /** 39 | * @brief Base template class for operators that swallow operands in reports. 40 | */ 41 | template 42 | struct op_report_without_operand : public op_report_without_operand_t, 43 | public enable_to_string 44 | { 45 | template 46 | static auto str(const T& b, 47 | std::enable_if_t< 48 | std::is_same::value, 49 | void* 50 | > = nullptr) 51 | { 52 | return b ? DerivedT::description : DerivedT::n_description; 53 | } 54 | 55 | template 56 | static auto n_str(const T& b, 57 | std::enable_if_t< 58 | std::is_same::value, 59 | void* 60 | > = nullptr) 61 | { 62 | return b ? DerivedT::n_description : DerivedT::description; 63 | } 64 | 65 | template 66 | static auto str(const T& b, 67 | std::enable_if_t< 68 | !std::is_same::value, 69 | void* 70 | > = nullptr) 71 | { 72 | std::ignore=b; 73 | return DerivedT::description; 74 | } 75 | 76 | template 77 | static auto n_str(const T& b, 78 | std::enable_if_t< 79 | !std::is_same::value, 80 | void* 81 | > = nullptr) 82 | { 83 | std::ignore=b; 84 | return DerivedT::n_description; 85 | } 86 | 87 | static auto str() 88 | { 89 | return DerivedT::description; 90 | } 91 | 92 | static auto n_str() 93 | { 94 | return DerivedT::n_description; 95 | } 96 | }; 97 | 98 | //------------------------------------------------------------- 99 | 100 | HATN_VALIDATOR_NAMESPACE_END 101 | 102 | #endif // HATN_VALIDATOR_OP_REPORT_WITHOUT_OPERAND_HPP 103 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/operator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/operator.hpp 12 | * 13 | * Defines base operator class. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OPERATOR_HPP 20 | #define HATN_VALIDATOR_OPERATOR_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | //------------------------------------------------------------- 30 | 31 | /** 32 | * @brief Tag for all operator clases. 33 | */ 34 | struct operator_tag 35 | { 36 | constexpr bool operator ==(const operator_tag&) const 37 | { 38 | return true; 39 | } 40 | constexpr bool operator !=(const operator_tag&) const 41 | { 42 | return false; 43 | } 44 | }; 45 | 46 | /** 47 | * @brief Base operator class. 48 | */ 49 | template 50 | struct op : public enable_to_string, 51 | public adjust_storable_ignore 52 | { 53 | using hana_tag=operator_tag; 54 | 55 | /** 56 | * @brief Get description of the operator to be used in reports. 57 | * @return String description of the operator. 58 | */ 59 | constexpr static const char* str() 60 | { 61 | return DerivedT::description; 62 | } 63 | 64 | /** 65 | * @brief Get description of inverted operator to be used in reports. 66 | * @return String description of inverted operator. 67 | */ 68 | constexpr static const char* n_str() 69 | { 70 | return DerivedT::n_description; 71 | } 72 | }; 73 | 74 | //------------------------------------------------------------- 75 | 76 | HATN_VALIDATOR_NAMESPACE_END 77 | 78 | #endif // HATN_VALIDATOR_OPERATOR_HPP 79 | -------------------------------------------------------------------------------- /include/hatn/validator/operators/string_patterns.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/operators/string_patterns.hpp 12 | * 13 | * Defines operator to validate some string patterns. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_STRING_PATTERNS_HPP 20 | #define HATN_VALIDATOR_STRING_PATTERNS_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | 29 | HATN_VALIDATOR_NAMESPACE_BEGIN 30 | 31 | //------------------------------------------------------------- 32 | 33 | /** 34 | * @brief Definition of operator "must contain only alpha symbols". 35 | */ 36 | struct str_alpha_t : public op_report_without_operand 37 | { 38 | constexpr static const char* description="must contain only letters and digits"; 39 | constexpr static const char* n_description="must contain not only letters and digits"; 40 | 41 | template 42 | bool operator() (const T1& a, const T2& b) const 43 | { 44 | static const std::regex e("[0-9a-zA-Z_]*"); 45 | return regex_match(a,e)==b; 46 | } 47 | }; 48 | 49 | /** 50 | @brief Operator "must contain only alpha symbols". 51 | */ 52 | constexpr str_alpha_t str_alpha{}; 53 | 54 | /** 55 | * @brief Definition of operator "must be hexadecimal number". 56 | */ 57 | struct str_hex_t : public op_report_without_operand 58 | { 59 | constexpr static const char* description="must be a hexadecimal number"; 60 | constexpr static const char* n_description="must be not a hexadecimal number"; 61 | 62 | template 63 | bool operator() (const T1& a, const T2& b) const 64 | { 65 | static const std::regex e("[0-9a-fA-F]+"); 66 | return regex_match(a,e)==b; 67 | } 68 | }; 69 | 70 | /** 71 | @brief Operator "must be hexadecimal number". 72 | */ 73 | constexpr str_hex_t str_hex{}; 74 | 75 | //------------------------------------------------------------- 76 | 77 | HATN_VALIDATOR_NAMESPACE_END 78 | 79 | #endif // HATN_VALIDATOR_STRING_PATTERNS_HPP 80 | -------------------------------------------------------------------------------- /include/hatn/validator/prepend_super_member.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/prepend_super_member.hpp 12 | * 13 | * Defines prepend_super_member. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PREPEND_SUPER_MEMBER_HPP 20 | #define HATN_VALIDATOR_PREPEND_SUPER_MEMBER_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | /** 27 | * @brief Prepend path of super member to path of current member. 28 | * @param super Super member. 29 | * @param member Current member. 30 | * @return Member with concatenated paths. If any of members have explicit names then new member is of member_with_name_list type. 31 | * 32 | * This helper is used with nested member validators. 33 | */ 34 | template 35 | auto prepend_super_member(SuperMemberT&& super, MemberT&& member); 36 | 37 | //------------------------------------------------------------- 38 | 39 | HATN_VALIDATOR_NAMESPACE_END 40 | 41 | #endif // HATN_VALIDATOR_PREPEND_SUPER_MEMBER_HPP 42 | -------------------------------------------------------------------------------- /include/hatn/validator/prepend_super_member.ipp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/prepend_super_member.ipp 12 | * 13 | * Defines prepend_super_member. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PREPEND_SUPER_MEMBER_IPP 20 | #define HATN_VALIDATOR_PREPEND_SUPER_MEMBER_IPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | template 29 | auto prepend_super_member(SuperMemberT&& super, MemberT&& member) 30 | { 31 | auto new_path=hana::concat(super.path(),member.path()); 32 | 33 | return hana::eval_if( 34 | hana::or_( 35 | std::is_base_of>{}, 36 | std::is_base_of>{} 37 | ), 38 | [&](auto&& _) 39 | { 40 | return make_member_with_name_list(make_member(_(new_path)), 41 | hana::concat(member_name_list(_(super)),member_name_list(_(member))) 42 | ); 43 | }, 44 | [&](auto&& _) 45 | { 46 | return make_member(_(new_path)); 47 | } 48 | ); 49 | } 50 | 51 | //------------------------------------------------------------- 52 | 53 | HATN_VALIDATOR_NAMESPACE_END 54 | 55 | #endif // HATN_VALIDATOR_PREPEND_SUPER_MEMBER_IPP 56 | -------------------------------------------------------------------------------- /include/hatn/validator/prevalidation/prevalidation_adapter_tag.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/prevalidation/prevalidation_adapter_tag.hpp 12 | * 13 | * Defines "prevalidation_adapter_tag". 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PREVALIDATION_ADAPTER_TAG_HPP 20 | #define HATN_VALIDATOR_PREVALIDATION_ADAPTER_TAG_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | struct prevalidation_adapter_tag{}; 29 | 30 | //------------------------------------------------------------- 31 | 32 | HATN_VALIDATOR_NAMESPACE_END 33 | 34 | #endif // HATN_VALIDATOR_PREVALIDATION_ADAPTER_TAG_HPP 35 | -------------------------------------------------------------------------------- /include/hatn/validator/prevalidation/validate_empty.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/prevalidation/validate_empty.hpp 12 | * 13 | * Defines helper to validate if object is empty. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_VALIDATE_EMPTY_HPP 20 | #define HATN_VALIDATOR_VALIDATE_EMPTY_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | /** 28 | * @brief Validate if object can be empty. 29 | * @param member Member name. 30 | * @param validator Validator to use for validation. If wrapped into strict_any then strict ANY validation will be invoked. 31 | * @param err Validation result. 32 | */ 33 | template 34 | void validate_empty( 35 | MemberT&& member, 36 | ValidatorT&& validator, 37 | error_report& err 38 | ) 39 | { 40 | validate(member[empty],wrap_strict_any(true,validator),extract_strict_any(validator),err); 41 | if (!err) 42 | { 43 | validate(member[size],wrap_strict_any(0,validator),extract_strict_any(validator),err); 44 | } 45 | } 46 | 47 | HATN_VALIDATOR_NAMESPACE_END 48 | 49 | #endif // HATN_VALIDATOR_VALIDATE_EMPTY_HPP 50 | -------------------------------------------------------------------------------- /include/hatn/validator/prevalidation/validate_value.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/prevalidation/validate_value.hpp 12 | * 13 | * Defines "validate_value" helpers. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_VALIDATE_VALUE_HPP 20 | #define HATN_VALIDATOR_VALIDATE_VALUE_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | /** 27 | * @brief Check if member's value can be validated by the validator. 28 | * @param member Member name. 29 | * @param val Value to set. 30 | * @param validator Validator to use for validation. 31 | * @param err Validation result. 32 | */ 33 | template 34 | void validate_value( 35 | MemberT&& member, 36 | ValueT&& val, 37 | ValidatorT&& validator, 38 | error_report& err 39 | ) 40 | { 41 | validate(member,wrap_strict_any(std::forward(val),validator),extract_strict_any(std::forward(validator)),err); 42 | } 43 | 44 | HATN_VALIDATOR_NAMESPACE_END 45 | 46 | #endif // HATN_VALIDATOR_VALIDATE_VALUE_HPP 47 | -------------------------------------------------------------------------------- /include/hatn/validator/properties.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties.hpp 12 | * 13 | * Includes all headers with properties. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PROPERTIES_HPP 20 | #define HATN_VALIDATOR_PROPERTIES_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | 29 | #include 30 | 31 | HATN_VALIDATOR_NAMESPACE_BEGIN 32 | 33 | //------------------------------------------------------------- 34 | 35 | //------------------------------------------------------------- 36 | 37 | HATN_VALIDATOR_NAMESPACE_END 38 | 39 | #endif // HATN_VALIDATOR_PROPERTIES_HPP 40 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/empty.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/size.hpp 12 | * 13 | * Defines "empty" property. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_EMPTY_HPP 20 | #define HATN_VALIDATOR_EMPTY_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | * @brief String descriptions helper for property "empty". 32 | */ 33 | struct string_empty_t : public enable_to_string 34 | { 35 | constexpr static const char* description="must be empty"; 36 | }; 37 | /** 38 | * @brief Instance of string descriptions helper for property "empty". 39 | */ 40 | constexpr string_empty_t string_empty{}; 41 | 42 | //------------------------------------------------------------- 43 | 44 | /** 45 | * @brief String descriptions helper for property "not empty". 46 | */ 47 | struct string_not_empty_t : public enable_to_string 48 | { 49 | constexpr static const char* description="must be not empty"; 50 | }; 51 | 52 | /** 53 | * @brief Instance of string descriptions helper for property "not empty". 54 | */ 55 | constexpr string_not_empty_t string_not_empty{}; 56 | 57 | HATN_VALIDATOR_PROPERTY_FLAG(empty,string_empty_t::description,string_not_empty_t::description) 58 | 59 | //------------------------------------------------------------- 60 | 61 | HATN_VALIDATOR_NAMESPACE_END 62 | 63 | #endif // HATN_VALIDATOR_EMPTY_HPP 64 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/h_size.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/h_size.hpp 12 | * 13 | * Defines special property "h_size" to get heterogeneous size of object. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_H_SIZE_HPP 20 | #define HATN_VALIDATOR_H_SIZE_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | /** 30 | * @brief Property for getting size of heterogeneous containers such as tuple size. 31 | */ 32 | struct type_h_size : public basic_property 33 | { 34 | template 35 | constexpr static size_t get(T&& v) 36 | { 37 | return hana::value(heterogeneous_size(v)); 38 | } 39 | template 40 | constexpr static bool has() 41 | { 42 | // applicable to any object because 43 | // size of non heterogeneous containers is zero 44 | return true; 45 | } 46 | template 47 | constexpr auto operator () (Args&&... args) const; 48 | 49 | constexpr static const char* name() 50 | { 51 | return "heterogeneous size"; 52 | } 53 | 54 | template 55 | constexpr static const char* flag_str(bool, const FormatterT&, bool =false) 56 | { 57 | return nullptr; 58 | } 59 | 60 | constexpr static bool has_flag_str() 61 | { 62 | return false; 63 | } 64 | 65 | template constexpr bool operator == (const T&&) const 66 | { 67 | return false; 68 | } 69 | template constexpr bool operator != (const T&&) const 70 | { 71 | return true; 72 | } 73 | constexpr bool operator == (const type_h_size&) const 74 | { 75 | return true; 76 | } 77 | constexpr bool operator != (const type_h_size&) const 78 | { 79 | return false; 80 | } 81 | }; 82 | constexpr type_h_size h_size{}; 83 | template 84 | constexpr auto type_h_size::operator () (Args&&... args) const 85 | { 86 | return make_property_validator(h_size,std::forward(args)...); 87 | } 88 | 89 | //------------------------------------------------------------- 90 | 91 | HATN_VALIDATOR_NAMESPACE_END 92 | 93 | #endif // HATN_VALIDATOR_H_SIZE_HPP 94 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/length.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/length.hpp 12 | * 13 | * Defines "length" property. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_LENGTH_HPP 20 | #define HATN_VALIDATOR_LENGTH_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | HATN_VALIDATOR_PROPERTY(length) 31 | 32 | //------------------------------------------------------------- 33 | 34 | HATN_VALIDATOR_NAMESPACE_END 35 | 36 | #endif // HATN_VALIDATOR_LENGTH_HPP 37 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/pair.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/pair.hpp 12 | * 13 | * Defines "first" and "second" properties to use with pairs/iterators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PAIR_HPP 20 | #define HATN_VALIDATOR_PAIR_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | HATN_VALIDATOR_PROPERTY(first) 30 | 31 | HATN_VALIDATOR_PROPERTY(second) 32 | 33 | //------------------------------------------------------------- 34 | 35 | HATN_VALIDATOR_NAMESPACE_END 36 | 37 | #endif // HATN_VALIDATOR_PAIR_HPP 38 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/size.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/size.hpp 12 | * 13 | * Defines "size" property. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_SIZE_HPP 20 | #define HATN_VALIDATOR_SIZE_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | HATN_VALIDATOR_PROPERTY(size) 30 | 31 | //------------------------------------------------------------- 32 | 33 | HATN_VALIDATOR_NAMESPACE_END 34 | 35 | #endif // HATN_VALIDATOR_SIZE_HPP 36 | -------------------------------------------------------------------------------- /include/hatn/validator/properties/value.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/properties/value.hpp 12 | * 13 | * Defines special property "value" that serves as proxy wrapper to the object itself. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_VALUE_HPP 20 | #define HATN_VALIDATOR_VALUE_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | /** 29 | * @brief Proxy wrapper that is used to get the object itself via property interface. 30 | */ 31 | struct type_p_value : public basic_property 32 | { 33 | template 34 | constexpr static T get(T&& v) 35 | { 36 | return hana::id(std::forward(v)); 37 | } 38 | template 39 | constexpr static bool has() 40 | { 41 | return true; 42 | } 43 | template 44 | constexpr auto operator () (Args&&... args) const; 45 | 46 | constexpr static const char* name() 47 | { 48 | return "value"; 49 | } 50 | 51 | template 52 | constexpr static const char* flag_str(bool, const FormatterT&, bool =false) 53 | { 54 | return nullptr; 55 | } 56 | 57 | constexpr static bool has_flag_str() 58 | { 59 | return false; 60 | } 61 | 62 | template constexpr bool operator == (const T&&) const 63 | { 64 | return false; 65 | } 66 | template constexpr bool operator != (const T&&) const 67 | { 68 | return true; 69 | } 70 | constexpr bool operator == (const type_p_value&) const 71 | { 72 | return true; 73 | } 74 | constexpr bool operator != (const type_p_value&) const 75 | { 76 | return false; 77 | } 78 | }; 79 | constexpr type_p_value value{}; 80 | template 81 | constexpr auto type_p_value::operator () (Args&&... args) const 82 | { 83 | return make_property_validator(value,std::forward(args)...); 84 | } 85 | 86 | //------------------------------------------------------------- 87 | 88 | HATN_VALIDATOR_NAMESPACE_END 89 | 90 | #endif // HATN_VALIDATOR_VALUE_HPP 91 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/aggregation_strings.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/aggregation_strings.hpp 12 | * 13 | * Defines description helpers for aggregation operators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_AGGREGATION_STRINGS_HPP 20 | #define HATN_VALIDATOR_AGGREGATION_STRINGS_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | //------------------------------------------------------------- 30 | 31 | struct aggregation_strings_tag; 32 | 33 | /** 34 | * @brief Helpers for aggregation strings. 35 | * 36 | * The helpers are used by strings object in formatting of aggreagation operators. 37 | * If customization of such strings is needed then another aggregation strings traits must be implemented 38 | * with the same methods signatures as in aggregation_strings_t. 39 | */ 40 | struct aggregation_strings_t 41 | { 42 | using hana_tag=aggregation_strings_tag; 43 | 44 | /** 45 | * @brief Get token for opening aggregation operator. 46 | * @param aggregation Descriptor of aggregation operation. 47 | * @return Opening token. 48 | */ 49 | static std::string open(const aggregation_op& aggregation) 50 | { 51 | return aggregation.open_token; 52 | } 53 | 54 | /** 55 | * @brief Get token for closing aggregation operator. 56 | * @param aggregation Descriptor of aggregation operation. 57 | * @return Closing token. 58 | */ 59 | static std::string close(const aggregation_op& aggregation) 60 | { 61 | return aggregation.close_token; 62 | } 63 | 64 | /** 65 | * @brief Get token for joining child validators within aggregation operator. 66 | * @param aggregation Descriptor of aggregation operation. 67 | * @return Separator token for join operation. 68 | */ 69 | static std::string conjunction(const aggregation_op& aggregation) 70 | { 71 | return aggregation.conjunction_token; 72 | } 73 | }; 74 | constexpr aggregation_strings_t aggregation_strings{}; 75 | 76 | //------------------------------------------------------------- 77 | 78 | /** 79 | * @brief String descriptions helper for conjunction "of". 80 | */ 81 | struct string_conjunction_of_t : public enable_to_string 82 | { 83 | constexpr static const char* description="of"; 84 | }; 85 | 86 | /** 87 | * @brief Instance of string descriptions helper for conjunction "of". 88 | */ 89 | constexpr string_conjunction_of_t string_conjunction_of{}; 90 | 91 | //------------------------------------------------------------- 92 | 93 | HATN_VALIDATOR_NAMESPACE_END 94 | 95 | #endif // HATN_VALIDATOR_AGGREGATION_STRINGS_HPP 96 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/extend_translator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/extend_translator.hpp 12 | * 13 | * Defines extended translator. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_EXTEND_TRANSLATOR_HPP 20 | #define HATN_VALIDATOR_EXTEND_TRANSLATOR_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief Translator estension. 31 | * 32 | * First try to translate using extension translator. If no translation found then use base translator. 33 | */ 34 | template 35 | struct extend_translator_t : public translator 36 | { 37 | /** 38 | * @brief Constructor. 39 | * @param base Base translator. 40 | * @param extension Translator to extend with. 41 | */ 42 | extend_translator_t( 43 | BaseTranslatorT&& base, 44 | ExtentionTranslatorT&& extension 45 | ) : base(std::forward(base)), 46 | extension(std::forward(extension)) 47 | {} 48 | 49 | /** 50 | * @brief Translate a string. 51 | * @param id String id. 52 | * @param cats Grammar categories to look for. 53 | * @return Translated string or id if such string not found. 54 | */ 55 | virtual translation_result translate(const std::string& id, grammar_categories cats=0) const override 56 | { 57 | auto result=extension.translate(id,cats); 58 | if (result) 59 | { 60 | return result; 61 | } 62 | return base.translate(id,cats); 63 | } 64 | 65 | BaseTranslatorT base; 66 | ExtentionTranslatorT extension; 67 | }; 68 | 69 | /** 70 | * @brief Create extended translator. 71 | * @param base Base translator. 72 | * @param extension Translator to extend with. 73 | * @return Translator with extension. 74 | * 75 | * Translator with extentions first tries to translate using extension. If no translation found then base translator is used. 76 | */ 77 | template 78 | auto extend_translator(BaseTranslatorT&& base, ExtentionTranslatorT&& extension) 79 | { 80 | return extend_translator_t{std::forward(base),std::forward(extension)}; 81 | } 82 | 83 | //------------------------------------------------------------- 84 | 85 | HATN_VALIDATOR_NAMESPACE_END 86 | 87 | #endif // HATN_VALIDATOR_EXTEND_TRANSLATOR_HPP 88 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/format_bool_operand.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/format_bool_operand.hpp 12 | * 13 | * Defines helper for formatting boolean operands. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_FORMAT_BOOL_OPERAND_HPP 20 | #define HATN_VALIDATOR_FORMAT_BOOL_OPERAND_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief String description helper for presentation of boolean true. 31 | */ 32 | struct string_true_t : public enable_to_string 33 | { 34 | constexpr static const char* description="true"; 35 | }; 36 | 37 | /** 38 | * @brief Instance of string description helper for presentation of boolean true. 39 | */ 40 | constexpr string_true_t string_true{}; 41 | 42 | /** 43 | * @brief String description helper for presentation of boolean false. 44 | */ 45 | struct string_false_t : public enable_to_string 46 | { 47 | constexpr static const char* description="false"; 48 | }; 49 | 50 | /** 51 | * @brief Instance of string description helper for presentation of boolean false. 52 | */ 53 | constexpr string_false_t string_false{}; 54 | 55 | /** 56 | * @brief Formatter of boolean operands. 57 | * 58 | * Formatter uses corresponding string description for presentation of boolean and then translates and decorates it 59 | * if "postprocess" argument is not false. 60 | */ 61 | template 62 | struct format_operand_t>::value>> 63 | { 64 | template 65 | concrete_phrase operator () (const TraitsT& traits, T1&& val, grammar_categories cats, bool postprocess) const 66 | { 67 | auto phrase=val?std::string(string_true):std::string(string_false); 68 | if (!postprocess) 69 | { 70 | return phrase; 71 | } 72 | return decorate(traits,translate(traits,std::move(phrase),cats)); 73 | } 74 | 75 | template 76 | auto operator () (const TraitsT& traits, T1&& val, grammar_categories cats) const 77 | { 78 | auto phrase=val?std::string(string_true):std::string(string_false); 79 | return decorate(traits,translate(traits,std::move(phrase),cats)); 80 | } 81 | }; 82 | 83 | //------------------------------------------------------------- 84 | 85 | HATN_VALIDATOR_NAMESPACE_END 86 | 87 | #endif // HATN_VALIDATOR_FORMAT_BOOL_OPERAND_HPP 88 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/mapped_translator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/mapped_translator.hpp 12 | * 13 | * Defines translator class that uses map of strings. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MAPPED_TRANSLATOR_HPP 20 | #define HATN_VALIDATOR_MAPPED_TRANSLATOR_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | #include 27 | #include 28 | 29 | HATN_VALIDATOR_NAMESPACE_BEGIN 30 | 31 | //------------------------------------------------------------- 32 | 33 | /** 34 | * @brief Mapped translator uses map of translated strings. 35 | * 36 | * Translator can be constructed with prepared map as 37 | * @code 38 | * mapped_translator{map}; 39 | * @endcode 40 | */ 41 | class mapped_translator : public translator 42 | { 43 | public: 44 | 45 | mapped_translator()=default; 46 | 47 | /** 48 | * @brief Constructor. 49 | * @param Translated strings. 50 | */ 51 | mapped_translator(std::map strings):_strings(std::move(strings)) 52 | {} 53 | 54 | /** 55 | * @brief Reset map. 56 | */ 57 | virtual void reset() override 58 | { 59 | _strings.clear(); 60 | } 61 | 62 | /** 63 | * @brief Translate a string. 64 | * @param id String id. 65 | * @return Translated string or id if such string not found. 66 | */ 67 | virtual translation_result translate(const std::string& id, grammar_categories =0) const override 68 | { 69 | auto it=_strings.find(id); 70 | if (it!=_strings.end()) 71 | { 72 | return translation_result{it->second,true}; 73 | } 74 | return translation_result{id,false}; 75 | } 76 | 77 | /** 78 | * @brief Get map of translated strings. 79 | * @return Map of translated strings. 80 | */ 81 | std::map& strings() noexcept 82 | { 83 | return _strings; 84 | } 85 | 86 | private: 87 | 88 | std::map _strings; 89 | }; 90 | 91 | //------------------------------------------------------------- 92 | 93 | HATN_VALIDATOR_NAMESPACE_END 94 | 95 | #endif // HATN_VALIDATOR_MAPPED_TRANSLATOR_HPP 96 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/member_operand.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/member_operand.hpp 12 | * 13 | * Defines wrapper of other member used as operand. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MEMBER_OPERAND_HPP 20 | #define HATN_VALIDATOR_MEMBER_OPERAND_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | struct member_operand_tag; 29 | 30 | /** 31 | * @brief Wrapper of member used as operand. 32 | */ 33 | template 34 | struct member_operand : public object_wrapper 35 | { 36 | using hana_tag=member_operand_tag; 37 | using object_wrapper::object_wrapper; 38 | }; 39 | 40 | /** 41 | @brief Make a member operand wrapper around member. 42 | @param b ID to wrap into member operand. 43 | @return Member operand. 44 | */ 45 | template 46 | auto make_member_operand(T&& b) 47 | { 48 | return member_operand{std::forward(b)}; 49 | } 50 | 51 | //------------------------------------------------------------- 52 | 53 | HATN_VALIDATOR_NAMESPACE_END 54 | 55 | #endif // HATN_VALIDATOR_MEMBER_OPERAND_HPP 56 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/no_translator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/no_translator.hpp 12 | * 13 | * Defines translator stub. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_NO_TRANSLATOR_HPP 20 | #define HATN_VALIDATOR_NO_TRANSLATOR_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | 27 | HATN_VALIDATOR_NAMESPACE_BEGIN 28 | 29 | //------------------------------------------------------------- 30 | 31 | /** 32 | * @brief Translator stub to use when no translation is needed. 33 | */ 34 | struct no_translator_t 35 | { 36 | using hana_tag=translator_tag; 37 | 38 | std::string operator() (const std::string& id, grammar_categories =0) const 39 | { 40 | return hana::id(id); 41 | } 42 | }; 43 | 44 | /** 45 | @brief Instance of translator stub to use when no translation is needed. 46 | */ 47 | constexpr no_translator_t no_translator{}; 48 | 49 | //------------------------------------------------------------- 50 | 51 | HATN_VALIDATOR_NAMESPACE_END 52 | 53 | #endif // HATN_VALIDATOR_NO_TRANSLATOR_HPP 54 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/order_and_presentation.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/order_and_presentation.hpp 12 | * 13 | * Defines helper that adjusts order and presentation of formatting. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ORDER_AND_PRESENTATION_HPP 20 | #define HATN_VALIDATOR_ORDER_AND_PRESENTATION_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | struct order_and_presentation_tag; 30 | 31 | /** 32 | * @brief Default helper for adjusting strings ordering and presentation. 33 | */ 34 | struct order_and_presentation_t 35 | { 36 | using hana_tag=order_and_presentation_tag; 37 | 38 | template 39 | void operator () (Args&&... args) const 40 | { 41 | detail::reorder_and_present(std::forward(args)...); 42 | } 43 | }; 44 | 45 | /** 46 | @brief Instance of default helper for adjusting strings ordering and presentation. 47 | */ 48 | constexpr order_and_presentation_t default_order_and_presentation{}; 49 | 50 | //------------------------------------------------------------- 51 | 52 | HATN_VALIDATOR_NAMESPACE_END 53 | 54 | #endif // HATN_VALIDATOR_ORDER_AND_PRESENTATION_HPP 55 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/original_member_names.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/original_member_names.hpp 12 | * 13 | * Defines original member names formatter. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ORIGINAL_MEMBER_NAMES_HPP 20 | #define HATN_VALIDATOR_ORIGINAL_MEMBER_NAMES_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Traits to format nested members as original names decorated with brackets. 30 | * 31 | * For example: ["field1"]["subfield1_1"]["subfield1_1_1"] will be formatted as [field1][subfield1_1][subfield1_1_1] 32 | */ 33 | struct original_member_names_traits_t : public dotted_member_names_traits_t 34 | { 35 | /** 36 | * @brief Get string for conjunction of nested member names. 37 | * @return String "." to use to join nested member names in the member's path. 38 | */ 39 | static auto member_names_conjunction() 40 | { 41 | return ""; 42 | } 43 | 44 | static auto member_property_conjunction() 45 | { 46 | return ""; 47 | } 48 | 49 | brackets_decorator_t decorator; 50 | }; 51 | 52 | /** 53 | @brief Formatter of member names in original format. 54 | 55 | For example: ["field1"]["subfield1_1"]["subfield1_1_1"] will be formatted as [field1][subfield1_1][subfield1_1_1] 56 | */ 57 | constexpr member_names original_member_names{original_member_names_traits_t{}}; 58 | 59 | //------------------------------------------------------------- 60 | 61 | HATN_VALIDATOR_NAMESPACE_END 62 | 63 | #endif // HATN_VALIDATOR_ORIGINAL_MEMBER_NAMES_HPP 64 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/prepare_operand_for_formatter.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/prepare_operand_for_formatter.hpp 12 | * 13 | * Defines helper for preparing operand for formatter. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_PREPARE_OPERAND_FORMATTER_HPP 20 | #define HATN_VALIDATOR_PREPARE_OPERAND_FORMATTER_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | /** 33 | * @brief Default helper to prepare operand for formatter. 34 | */ 35 | template > 36 | struct prepare_operand_for_formatter_t 37 | { 38 | auto operator () (OpT&&, T&& b) const -> decltype(auto) 39 | { 40 | return hana::id(std::forward(b)); 41 | } 42 | }; 43 | 44 | /** 45 | * @brief Helper to prepare operand for formatter for operator contains. 46 | */ 47 | template 48 | struct prepare_operand_for_formatter_t,contains_t>::value 51 | > 52 | > 53 | { 54 | auto operator () (OpT&&, T&& b) const -> decltype(auto) 55 | { 56 | return make_member_operand( 57 | make_plain_member(std::forward(b)) 58 | ); 59 | } 60 | }; 61 | 62 | /** 63 | * @brief Template instance of helper for preparing operand for formatter. 64 | */ 65 | template 66 | constexpr prepare_operand_for_formatter_t prepare_operand_for_formatter_inst{}; 67 | 68 | /** 69 | * @brief Prepare operand for formatter taking into account operator. 70 | * @param op Operator. 71 | * @param b Original operand. 72 | * @return Operand prepared for formatting. 73 | */ 74 | template 75 | auto prepare_operand_for_formatter(OpT&& op, T&& b) 76 | { 77 | return prepare_operand_for_formatter_inst(std::forward(op),std::forward(b)); 78 | } 79 | 80 | //------------------------------------------------------------- 81 | 82 | HATN_VALIDATOR_NAMESPACE_END 83 | 84 | #endif // HATN_VALIDATOR_PREPARE_OPERAND_FORMATTER_HPP 85 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/prepare_property_formatting.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/prepare_property_formatting.hpp 12 | * 13 | * Defines "prepare_property_formatting" helper. 14 | * Currently not used. 15 | * 16 | */ 17 | 18 | /****************************************************************************/ 19 | 20 | #ifndef HATN_VALIDATOR_PREPARE_PROPERTY_FORMATTING_HPP 21 | #define HATN_VALIDATOR_PREPARE_PROPERTY_FORMATTING_HPP 22 | 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | /** 33 | * @brief Currently not used. 34 | */ 35 | #ifdef HATN_VALIDATOR_PREPARE_PROPERTY_FORMATTING 36 | struct prepare_property_formatting_impl 37 | { 38 | template 39 | auto operator() (StringsFmtT&& strings, MemberNamesFmtT&& mn, PropT&& prop) const 40 | { 41 | return hana::eval_if( 42 | std::is_base_of>{}, 43 | [&](auto&& _) 44 | { 45 | return prepare_variadic_property_formatting(_(strings),_(mn),_(prop)); 46 | }, 47 | [&](auto&& _) 48 | { 49 | return fmt_pair(_(mn),_(prop)); 50 | } 51 | ); 52 | } 53 | }; 54 | constexpr prepare_property_formatting_impl prepare_property_formatting{}; 55 | #endif 56 | 57 | //------------------------------------------------------------- 58 | HATN_VALIDATOR_NAMESPACE_END 59 | 60 | #endif // HATN_VALIDATOR_PREPARE_PROPERTY_FORMATTING_HPP 61 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/quotes_decorator.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/decorator.hpp 12 | * 13 | * Defines quotes decorator. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_QUOTES_DECORATOR_HPP 20 | #define HATN_VALIDATOR_QUOTES_DECORATOR_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | 29 | HATN_VALIDATOR_NAMESPACE_BEGIN 30 | 31 | //------------------------------------------------------------- 32 | 33 | namespace detail 34 | { 35 | /** 36 | * @brief Default helper for quotes decorator. 37 | */ 38 | template > 39 | struct quotes_decorator_helper 40 | { 41 | static auto f(T&& val) -> decltype(auto) 42 | { 43 | return hana::id(std::forward(val)); 44 | } 45 | }; 46 | 47 | /** 48 | * @brief Helper for quotes decorator when argument is a concrete_phrase. 49 | */ 50 | template 51 | struct quotes_decorator_helper>::value>> 53 | { 54 | static auto f(T&& val) -> decltype(auto) 55 | { 56 | std::string str; 57 | backend_formatter.append(str,"\"",std::string(std::forward(val)),"\""); 58 | return concrete_phrase(std::move(str),val.grammar_cats()); 59 | } 60 | }; 61 | 62 | /** 63 | * @brief Helper for quotes decorator when argument can be used to construct std::string but is not a concrete_phrase. 64 | */ 65 | template 66 | struct quotes_decorator_helper::value 68 | && 69 | !std::is_same>::value 70 | >> 71 | { 72 | static auto f(T&& val) -> decltype(auto) 73 | { 74 | std::string str; 75 | backend_formatter.append(str,"\"",std::string(std::forward(val)),"\""); 76 | return str; 77 | } 78 | }; 79 | } 80 | 81 | /** 82 | * @brief Quotes decorator that adds quotes around original string. 83 | */ 84 | struct quotes_decorator_t 85 | { 86 | using hana_tag=decorator_tag; 87 | 88 | template 89 | auto operator() (T&& val) const -> decltype(auto) 90 | { 91 | return detail::quotes_decorator_helper::f(std::forward(val)); 92 | } 93 | }; 94 | constexpr quotes_decorator_t quotes_decorator{}; 95 | 96 | //------------------------------------------------------------- 97 | 98 | HATN_VALIDATOR_NAMESPACE_END 99 | 100 | #endif // HATN_VALIDATOR_QUOTES_DECORATOR_HPP 101 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/report_aggregation.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/report_aggregation.hpp 12 | * 13 | * Defines descriptor of report aggregation. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_report_aggregation_HPP 20 | #define HATN_VALIDATOR_report_aggregation_HPP 21 | 22 | #include 23 | #include 24 | 25 | #include 26 | #include 27 | 28 | HATN_VALIDATOR_NAMESPACE_BEGIN 29 | 30 | //------------------------------------------------------------- 31 | 32 | struct report_aggregation_tag; 33 | 34 | /** 35 | * @brief Descriptor of base aggregation operator used in validation report. 36 | */ 37 | struct empty_report_aggregation 38 | { 39 | using hana_tag=report_aggregation_tag; 40 | 41 | /** 42 | * @brief Constructor. 43 | * @param aggregation Aggregation operation. 44 | * @param member Member the operation is applied to. 45 | */ 46 | empty_report_aggregation( 47 | aggregation_op aggregation, 48 | std::string member=std::string() 49 | ) : aggregation(std::move(aggregation)), 50 | member(std::move(member)), 51 | single(true), 52 | any_all_count( 53 | static_cast(aggregation.id==aggregation_id::ANY || aggregation.id==aggregation_id::ALL) 54 | ), 55 | parts_count(0) 56 | {} 57 | 58 | aggregation_op aggregation; 59 | 60 | std::string member; 61 | 62 | bool single; 63 | size_t any_all_count; 64 | 65 | int parts_count; 66 | }; 67 | 68 | 69 | /** 70 | * @brief Descriptor of aggregation operator used in validation report. 71 | */ 72 | template 73 | struct report_aggregation : public empty_report_aggregation 74 | { 75 | using empty_report_aggregation::empty_report_aggregation; 76 | 77 | std::vector parts; 78 | }; 79 | 80 | //------------------------------------------------------------- 81 | 82 | HATN_VALIDATOR_NAMESPACE_END 83 | 84 | #endif // HATN_VALIDATOR_report_aggregation_HPP 85 | -------------------------------------------------------------------------------- /include/hatn/validator/reporting/translate.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/reporting/translate.hpp 12 | * 13 | * Defines helper for translating using object that can optionally have or not have translators. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_TRANSLATE_HPP 20 | #define HATN_VALIDATOR_TRANSLATE_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | * @brief Helper for translating strings with object that can optionally have or not have translator. 32 | * 33 | * Version for object that does not have translator. 34 | */ 35 | template 36 | struct translate_t 37 | { 38 | template 39 | constexpr auto operator() (T1&&, Arg1&& arg, grammar_categories) const -> decltype(auto) 40 | { 41 | return hana::id(std::forward(arg)); 42 | } 43 | }; 44 | 45 | /** 46 | * @brief Helper for translating strings with object that can optionally have or not have translator 47 | * 48 | * Version for object that has translator. 49 | */ 50 | template 51 | struct translate_t>().translator(std::declval>(),std::declval()) 54 | )> 55 | { 56 | template 57 | auto operator() (T1&& obj, Arg1&& arg, grammar_categories grammar_cats=0) const -> decltype(auto) 58 | { 59 | return obj.translator(std::forward(arg),grammar_cats); 60 | } 61 | }; 62 | 63 | /** 64 | * @brief Instance of helper for translating strings with object that can optionally have or not have translator. 65 | */ 66 | template 67 | constexpr translate_t translate_inst{}; 68 | 69 | /** 70 | * @brief Translate a phrase. 71 | * @param obj Object that can have or not have a translator. 72 | * @param phrase Phrase to translate if applicable. 73 | * @param 74 | * @return If object has translator then translated phrase or phrase "as is" otherwise. 75 | */ 76 | template 77 | constexpr auto translate(T&& obj, PhraseT&& phrase, grammar_categories grammar_cats=0) -> decltype(auto) 78 | { 79 | return translate_inst(std::forward(obj),std::forward(phrase),grammar_cats); 80 | } 81 | 82 | //------------------------------------------------------------- 83 | 84 | HATN_VALIDATOR_NAMESPACE_END 85 | 86 | #endif // HATN_VALIDATOR_TRANSLATE_HPP 87 | -------------------------------------------------------------------------------- /include/hatn/validator/status.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/status.hpp 12 | * 13 | * Defines status of validation operations. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_STATUS_HPP 20 | #define HATN_VALIDATOR_STATUS_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Status to be used as result of validation operation 30 | */ 31 | class status 32 | { 33 | public: 34 | 35 | enum class code : int 36 | { 37 | success, 38 | fail, 39 | ignore 40 | }; 41 | 42 | /** 43 | * @brief Default constructor. 44 | */ 45 | status() noexcept : _code(code::success) 46 | {} 47 | 48 | /** 49 | * @brief Constructor from code. 50 | * @param c Status code. 51 | */ 52 | status(code c) noexcept : _code(c) 53 | {} 54 | 55 | /** 56 | * @brief Constructor from boolean. 57 | * @param ok Boolean status. 58 | */ 59 | status(bool ok) noexcept : _code(ok?code::success:code::fail) 60 | {} 61 | 62 | /** 63 | * @brief Convert to boolean. 64 | */ 65 | operator bool () const noexcept 66 | { 67 | return _code!=code::fail; 68 | } 69 | 70 | /** 71 | * @brief Get code value. 72 | * @return Status code. 73 | */ 74 | code value() const noexcept 75 | { 76 | return _code; 77 | } 78 | 79 | void reset(code value=code::success) noexcept 80 | { 81 | _code=value; 82 | } 83 | 84 | bool operator == (const code& val) const noexcept 85 | { 86 | return val==_code; 87 | } 88 | bool operator != (const code& val) const noexcept 89 | { 90 | return val!=_code; 91 | } 92 | 93 | bool success() const noexcept 94 | { 95 | return _code==code::success; 96 | } 97 | 98 | bool fail() const noexcept 99 | { 100 | return _code==code::fail; 101 | } 102 | 103 | bool ignore() const noexcept 104 | { 105 | return _code==code::ignore; 106 | } 107 | 108 | private: 109 | 110 | code _code; 111 | }; 112 | 113 | struct status_predicate_or_t 114 | { 115 | bool operator() (const status& v) const 116 | { 117 | return v.value()!=status::code::success; 118 | } 119 | }; 120 | constexpr status_predicate_or_t status_predicate_or{}; 121 | 122 | //------------------------------------------------------------- 123 | 124 | HATN_VALIDATOR_NAMESPACE_END 125 | 126 | #endif // HATN_VALIDATOR_STATUS_HPP 127 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/adjust_storable_ignore.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/adjust_storable_ignore.hpp 12 | * 13 | * Defines adjust_storable_ignore. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ADJUST_STORABLE_IGNORE_HPP 20 | #define HATN_VALIDATOR_ADJUST_STORABLE_IGNORE_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Struct to be used as a base struct for objects that must be copied as is to adjust_storable_t wrapper. 30 | */ 31 | struct adjust_storable_ignore{}; 32 | 33 | //------------------------------------------------------------- 34 | 35 | HATN_VALIDATOR_NAMESPACE_END 36 | 37 | #endif // HATN_VALIDATOR_ADJUST_STORABLE_IGNORE_HPP 38 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/adjust_storable_type.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/adjust_storable_type.hpp 12 | * 13 | * Defines helpers for adjusting types used as storable elements in tuples. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ADJUST_STORABLE_TYPE_HPP 20 | #define HATN_VALIDATOR_ADJUST_STORABLE_TYPE_HPP 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | 30 | HATN_VALIDATOR_NAMESPACE_BEGIN 31 | 32 | //------------------------------------------------------------- 33 | 34 | /** 35 | * @brief Helper for adjusting types for storage in validator. 36 | * By default all storable objects are put into object_wrapper. 37 | */ 38 | template > 39 | struct adjust_storable_type 40 | { 41 | using type=object_wrapper; 42 | }; 43 | 44 | /** 45 | * @brief Adjust const char* that must be stored as std::string. 46 | */ 47 | template 48 | struct adjust_storable_type::value> 50 | > 51 | { 52 | using type=std::string; 53 | }; 54 | 55 | /** 56 | * @brief Adjust is_constant_size types that must be stored wrapped into heterogeneous_property_just_index_t. 57 | */ 58 | template 59 | struct adjust_storable_type>::value> 61 | > 62 | { 63 | using type=heterogeneous_property_just_index_t::value>; 64 | }; 65 | 66 | /** 67 | * @brief Adjust special types that must be stored as copies. 68 | */ 69 | template 70 | struct adjust_storable_type>::value 73 | > 74 | > 75 | { 76 | using type=std::decay_t; 77 | }; 78 | 79 | /** 80 | * @brief Implementer of adjust_storable. 81 | */ 82 | struct adjust_storable_impl 83 | { 84 | template 85 | auto operator () (T&& v) const 86 | { 87 | return typename adjust_storable_type::type{std::forward(v)}; 88 | } 89 | }; 90 | /** 91 | * @brief Make storable type from a variable. 92 | * @param v Value to adjust. 93 | * @return Inpout value adjusted to storable type. 94 | */ 95 | constexpr adjust_storable_impl adjust_storable{}; 96 | 97 | HATN_VALIDATOR_NAMESPACE_END 98 | 99 | #endif // HATN_VALIDATOR_ADJUST_STORABLE_TYPE_HPP 100 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/copy.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/copy.hpp 12 | * 13 | * Defines helper for explicit variable copying. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_COPY_HPP 20 | #define HATN_VALIDATOR_COPY_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Implementer of copy(). 30 | */ 31 | struct copy_impl 32 | { 33 | template 34 | T operator () (const T& v) const 35 | { 36 | return v; 37 | } 38 | }; 39 | /** 40 | * @brief Explicitly copy a variable. 41 | * @param v Value to copy. 42 | * @return Copied variable. 43 | */ 44 | constexpr copy_impl copy{}; 45 | 46 | //------------------------------------------------------------- 47 | 48 | HATN_VALIDATOR_NAMESPACE_END 49 | 50 | #endif // HATN_VALIDATOR_COPY_HPP 51 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/enable_to_string.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/enable_to_string.hpp 12 | * 13 | * Defines base template for types that can be string convertible using description. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_ENABLE_TO_STRING_HPP 20 | #define HATN_VALIDATOR_ENABLE_TO_STRING_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | //------------------------------------------------------------- 28 | 29 | /** 30 | * @brief Base template for types that can be string convertible using static description. 31 | */ 32 | template 33 | struct enable_to_string 34 | { 35 | operator std::string () const 36 | { 37 | return std::string(DerivedT::description); 38 | } 39 | }; 40 | 41 | //------------------------------------------------------------- 42 | 43 | HATN_VALIDATOR_NAMESPACE_END 44 | 45 | #endif // HATN_VALIDATOR_ENABLE_TO_STRING_HPP 46 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/get_it.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/get_it.hpp 12 | * 13 | * Defines helper for getting value from container's iterator. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_GET_IT_HPP 20 | #define HATN_VALIDATOR_GET_IT_HPP 21 | 22 | #include 23 | #include 24 | 25 | HATN_VALIDATOR_NAMESPACE_BEGIN 26 | 27 | /** 28 | * @brief Helper for getting value from container's iterator. 29 | */ 30 | template > 31 | struct get_it_t 32 | { 33 | template 34 | constexpr auto operator() (T1&& it) const -> decltype(auto) 35 | { 36 | auto& val=*it; 37 | return val; 38 | } 39 | 40 | template 41 | constexpr static auto key(T1&& it) -> decltype(auto) 42 | { 43 | auto& val=*it; 44 | return val; 45 | } 46 | }; 47 | 48 | /** 49 | * @brief Helper for getting value from container's iterator when iterator can be converted to std::pair. 50 | * 51 | * Used for std::map, etc. 52 | */ 53 | template 54 | struct get_it_t())>::value> 56 | > 57 | { 58 | template 59 | constexpr auto operator() (T1&& it) const -> decltype(auto) 60 | { 61 | auto& val=it->second; 62 | return val; 63 | } 64 | 65 | template 66 | constexpr static auto key(T1&& it) -> decltype(auto) 67 | { 68 | auto& val=it->first; 69 | return val; 70 | } 71 | }; 72 | /** 73 | * @brief Instance of helper for getting value from container's iterator. 74 | */ 75 | template 76 | constexpr get_it_t get_it_impl{}; 77 | 78 | /** 79 | * @brief Get value from iterator. 80 | * @param it Iterator to get value from. 81 | * @return Reference to iterator's value. 82 | */ 83 | template 84 | constexpr auto get_it(T&& it) -> decltype(auto) 85 | { 86 | return get_it_impl(std::forward(it)); 87 | } 88 | 89 | template 90 | constexpr auto key_it(T&& it) -> decltype(auto) 91 | { 92 | return get_it_impl.key(std::forward(it)); 93 | } 94 | 95 | HATN_VALIDATOR_NAMESPACE_END 96 | 97 | #endif // HATN_VALIDATOR_GET_IT_HPP 98 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/hana_to_std_tuple.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/hana_to_std_tuple.hpp 12 | * 13 | * Defines converter of hana::tuple to std::tuple. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_HANA_TO_STD_TUPLE_HPP 20 | #define HATN_VALIDATOR_HANA_TO_STD_TUPLE_HPP 21 | 22 | #include 23 | 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | @brief Convert hana::tuple to std::tuple. 32 | */ 33 | template 34 | auto hana_to_std_tuple(Ts&& ts) 35 | { 36 | return hana::to(std::forward(ts)); 37 | } 38 | 39 | /** 40 | @brief Convert std::tuple to hana::tuple. 41 | */ 42 | template 43 | auto std_to_hana_tuple(Ts&& ts) 44 | { 45 | return hana::to_tuple(std::forward(ts)); 46 | } 47 | 48 | /** 49 | @brief Get size of hana tuple. 50 | */ 51 | template 52 | using hana_tuple_size=hana::size_t>()))>::value>; 53 | 54 | /** 55 | @brief Check if hana tuple is empty. 56 | */ 57 | template 58 | using hana_tuple_empty=hana::bool_::value==0>; 59 | 60 | //------------------------------------------------------------- 61 | 62 | HATN_VALIDATOR_NAMESPACE_END 63 | 64 | #endif // HATN_VALIDATOR_HANA_TO_STD_TUPLE_HPP 65 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/has_reset.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/has_reset.hpp 12 | * 13 | * Defines helper for checking if class has reset() method. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_HAS_RESET_HPP 20 | #define HATN_VALIDATOR_HAS_RESET_HPP 21 | 22 | #include 23 | 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | struct has_reset_t 31 | { 32 | template 33 | auto operator()(T arg) const 34 | { 35 | return hana::is_valid([](auto v) -> decltype((void)hana::traits::declval(v).reset()){})(arg); 36 | } 37 | }; 38 | 39 | constexpr has_reset_t has_reset{}; 40 | 41 | //------------------------------------------------------------- 42 | 43 | HATN_VALIDATOR_NAMESPACE_END 44 | 45 | #endif // HATN_VALIDATOR_HAS_RESET_HPP 46 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/is_pair.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/is_pair.hpp 12 | * 13 | * Defines helper to check if object is of std::pair type. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_IS_PAIR_HPP 20 | #define HATN_VALIDATOR_IS_PAIR_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | namespace detail { 29 | 30 | /** 31 | * @brief Default helper to check if object has property "first". 32 | */ 33 | template 34 | struct has_first 35 | { 36 | constexpr static const bool value=false; 37 | }; 38 | 39 | /** 40 | * @brief Helper to check if object has property "first" when it has. 41 | */ 42 | template 43 | struct has_first>().first) 45 | > 46 | { 47 | constexpr static const bool value=true; 48 | }; 49 | 50 | /** 51 | * @brief Default helper to check if object has property "second". 52 | */ 53 | template 54 | struct has_second 55 | { 56 | constexpr static const bool value=false; 57 | }; 58 | 59 | /** 60 | * @brief Helper to check if object has property "second" for the case when it has indeed. 61 | */ 62 | template 63 | struct has_second>().second)> 65 | { 66 | constexpr static const bool value=true; 67 | }; 68 | } 69 | 70 | /** 71 | * @brief Default helper to check if object is of std::pair type. i.e it has "first" and "second" properties. 72 | */ 73 | template > 74 | struct is_pair_t 75 | { 76 | constexpr static const bool value=false; 77 | }; 78 | 79 | /** 80 | * @brief Helper to check if object is of std::pair type. i.e it has "first" and "second" properties. 81 | */ 82 | template 83 | struct is_pair_t::value && detail::has_second::value> 85 | > 86 | { 87 | constexpr static const bool value=true; 88 | }; 89 | 90 | /** 91 | * @brief Check if object is a std::pair. 92 | * @param v Variable to check. 93 | * @return true if the object has first and second member variables defined. 94 | */ 95 | template 96 | constexpr auto is_pair(T&& v) 97 | { 98 | std::ignore=v; 99 | return is_pair_t::value; 100 | } 101 | 102 | //------------------------------------------------------------- 103 | 104 | HATN_VALIDATOR_NAMESPACE_END 105 | 106 | #endif // HATN_VALIDATOR_IS_PAIR_HPP 107 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/make_types_tuple.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/make_types_tuple.hpp 12 | * 13 | * Defines helper to create a tuple of types from variadic arguments. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_MAKE_TYPES_TUPLE_HPP 20 | #define HATN_VALIDATOR_MAKE_TYPES_TUPLE_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | @brief Make tuple of hana::type_c<> from variadic arguments. 30 | */ 31 | template 32 | constexpr auto make_types_tuple(Args&&...) 33 | { 34 | return hana::tuple_t...>; 35 | } 36 | 37 | //------------------------------------------------------------- 38 | 39 | HATN_VALIDATOR_NAMESPACE_END 40 | 41 | #endif // HATN_VALIDATOR_MAKE_TYPES_TUPLE_HPP 42 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/optional.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/optional.hpp 12 | * 13 | * Defines alias for optional: boost::optional is used for C++14 standard and std::optional is used for C++17 and newer stansards. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_OPTIONAL_HPP 20 | #define HATN_VALIDATOR_OPTIONAL_HPP 21 | 22 | #if __cplusplus < 201703L || (defined (IOS_SDK_VERSION_X10) && IOS_SDK_VERSION_X10<120) 23 | #include 24 | #else 25 | #include 26 | #endif 27 | 28 | #include 29 | 30 | HATN_VALIDATOR_NAMESPACE_BEGIN 31 | 32 | //------------------------------------------------------------- 33 | 34 | #if __cplusplus < 201703L || (defined (IOS_SDK_VERSION_X10) && IOS_SDK_VERSION_X10<120) 35 | template 36 | using optional=boost::optional; 37 | #else 38 | template 39 | using optional=std::optional; 40 | #endif 41 | 42 | //------------------------------------------------------------- 43 | 44 | HATN_VALIDATOR_NAMESPACE_END 45 | 46 | #endif // HATN_VALIDATOR_OPTIONAL_HPP 47 | -------------------------------------------------------------------------------- /include/hatn/validator/utils/wrap_object.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/utils/make_object_wrapper.hpp 12 | * 13 | * Defines helpers for making object wrappers. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_WRAP_OBJECT_HPP 20 | #define HATN_VALIDATOR_WRAP_OBJECT_HPP 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | HATN_VALIDATOR_NAMESPACE_BEGIN 27 | 28 | //------------------------------------------------------------- 29 | 30 | /** 31 | * @brief Wrap a value into object_wrapper if it is not an object_wrapper already. 32 | * @param v Value. 33 | * @return object_wrapper if value is not an object_wrapper, otherwise value as is. 34 | */ 35 | struct wrap_object_impl 36 | { 37 | template 38 | auto operator () (T&& v) const -> decltype(auto) 39 | { 40 | return hana::eval_if( 41 | hana::is_a, 42 | [&](auto&& _) -> decltype(auto) 43 | { 44 | return hana::id(_(v)); 45 | }, 46 | [&](auto&& _) 47 | { 48 | return object_wrapper(std::forward(_(v))); 49 | } 50 | ); 51 | } 52 | }; 53 | constexpr wrap_object_impl wrap_object{}; 54 | 55 | //------------------------------------------------------------- 56 | /** 57 | * @brief Wrap a reference to an object into object_wrapper if object is already wrapped by another object_wrapper. 58 | * @param v Value. 59 | * @return A wrapped reference if value is a object_wrapper, otherwise the value as is. 60 | * 61 | * This helper is used to avoid extra copies of object_wrapper embeddable in cases when object_wrapper wraps rvalue. 62 | * In this case the original object_wrapper with actual storable value will be transformed to object_wrapper 63 | * with constant reference to the value. 64 | */ 65 | template 66 | auto wrap_object_ref(T&& v) -> decltype(auto) 67 | { 68 | return hana::eval_if( 69 | hana::and_( 70 | hana::is_a, 71 | hana::not_(std::is_base_of>{}) 72 | ), 73 | [&](auto&& _) 74 | { 75 | const auto& val=unwrap_object(_(v)); 76 | return object_wrapper(val); 77 | }, 78 | [&](auto&& _) -> decltype(auto) 79 | { 80 | return hana::id(_(v)); 81 | } 82 | ); 83 | } 84 | 85 | //------------------------------------------------------------- 86 | 87 | HATN_VALIDATOR_NAMESPACE_END 88 | 89 | #endif // HATN_VALIDATOR_WRAP_OBJECT_HPP 90 | -------------------------------------------------------------------------------- /include/hatn/validator/variadic_arg_tag.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/variadic_arg_tag.hpp 12 | * 13 | * Defines tags of variadic arguments. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_VARIADIC_ARG_TAG_HPP 20 | #define HATN_VALIDATOR_VARIADIC_ARG_TAG_HPP 21 | 22 | #include 23 | 24 | HATN_VALIDATOR_NAMESPACE_BEGIN 25 | 26 | //------------------------------------------------------------- 27 | 28 | /** 29 | * @brief Base tag of variadic arguments. 30 | */ 31 | struct variadic_arg_tag{}; 32 | 33 | /** 34 | * @brief Base tag of variadic arguments with element aggregations. 35 | */ 36 | struct variadic_arg_aggregation_tag{}; 37 | 38 | //------------------------------------------------------------- 39 | 40 | HATN_VALIDATOR_NAMESPACE_END 41 | 42 | #endif // HATN_VALIDATOR_VARIADIC_ARG_TAG_HPP 43 | -------------------------------------------------------------------------------- /include/hatn/validator/version.hpp: -------------------------------------------------------------------------------- 1 | /** 2 | @copyright Evgeny Sidorov 2020 3 | 4 | Distributed under the Boost Software License, Version 1.0. 5 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 6 | 7 | */ 8 | 9 | /****************************************************************************/ 10 | 11 | /** @file validator/version.hpp 12 | * 13 | * Defines macros for tracking the version of the library. 14 | * 15 | */ 16 | 17 | /****************************************************************************/ 18 | 19 | #ifndef HATN_VALIDATOR_VERSION_HPP 20 | #define HATN_VALIDATOR_VERSION_HPP 21 | 22 | //! @internal 23 | //! Transforms a (version, revision, patchlevel) triple into a number of the 24 | //! form 0xVVRRPPPP to allow comparing versions in a normalized way. 25 | //! 26 | //! See http://sourceforge.net/p/predef/wiki/VersionNormalization. 27 | #define HATN_VALIDATOR_CONFIG_VERSION(version, revision, patch) \ 28 | (((version) << 24) + ((revision) << 16) + (patch)) 29 | 30 | //! @ingroup group-config 31 | //! Macro expanding to the major version of the library, i.e. the `x` in `x.y.z`. 32 | #define HATN_VALIDATOR_MAJOR_VERSION 2 33 | 34 | //! @ingroup group-config 35 | //! Macro expanding to the minor version of the library, i.e. the `y` in `x.y.z`. 36 | #define HATN_VALIDATOR_MINOR_VERSION 1 37 | 38 | //! @ingroup group-config 39 | //! Macro expanding to the patch level of the library, i.e. the `z` in `x.y.z`. 40 | #define HATN_VALIDATOR_PATCH_VERSION 1 41 | 42 | //! @ingroup group-config 43 | //! Macro expanding to the full version of the library, in hexadecimal 44 | //! representation. 45 | #define HATN_VALIDATOR_VERSION \ 46 | HATN_VALIDATOR_CONFIG_VERSION(HATN_VALIDATOR_MAJOR_VERSION, \ 47 | HATN_VALIDATOR_MINOR_VERSION, \ 48 | HATN_VALIDATOR_PATCH_VERSION) \ 49 | 50 | #endif // HATN_VALIDATOR_VERSION_HPP 51 | -------------------------------------------------------------------------------- /sample-build/linux-clang.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | export BOOST_ROOT=$PWD/deps/root-clang 4 | export FMT_ROOT=$PWD/deps/fmt 5 | 6 | export CXX=clang++ 7 | export BUILD_TYPE=Release 8 | 9 | export BUILD_DIR=$PWD/build/cpp-validator/build 10 | export INSTALL_DIR=$PWD/build/cpp-validator/install 11 | export SRC_DIR=$PWD/cpp-validator 12 | 13 | if [ -d "$BUILD_DIR" ]; then 14 | rm -rf $BUILD_DIR 15 | fi 16 | 17 | if [ -d "$INSTALL_DIR" ]; then 18 | rm -rf $INSTALL_DIR 19 | fi 20 | 21 | mkdir -p $BUILD_DIR 22 | cd $BUILD_DIR 23 | 24 | cmake -G "Unix Makefiles" \ 25 | -DCMAKE_INSTALL_PREFIX=$INSTALL_DIR \ 26 | -DCMAKE_BUILD_TYPE=$BUILD_TYPE \ 27 | -DVALIDATOR_WITH_TESTS=On \ 28 | -DVALIDATOR_WITH_EXAMPLES=On \ 29 | -DVALIDATOR_WITH_FMT=On \ 30 | $SRC_DIR 31 | make -j8 32 | ctest -VV 33 | cd - 34 | 35 | #$BUILD_DIR/test/hatnvalidator-test --log_level=test_suite 36 | -------------------------------------------------------------------------------- /sample-build/readme.txt: -------------------------------------------------------------------------------- 1 | Sample scripts to build and run tests. 2 | Run a script from a folder where source folder (cpp-validator) resides. 3 | Ensure that variables in a script fit your environment. 4 | 5 | BOOST_ROOT - root folder where boost is installed 6 | FMT_ROOT - root folder where libfmt is installed 7 | 8 | BUILD_TYPE - Release/Debug build type 9 | 10 | CXX (linux only) - name of C++ compiler (e.g. clang++) 11 | 12 | CMAKE_PATH (windows only) - path where CMake is installed on Windows (e.g. C:\Program Files\CMake\bin) 13 | MSVC_ROOT (windows only) - path where Microsoft Visual C++ is installed (e.g. C:\Program Files (x86)\Microsoft Visual Studio\2019\Community) 14 | MSVC_COMPILER (windows only) - string representing version of MSVC compiler (e.g. v142) 15 | COMPILER_VERSION (windows only) - version of MSVC compiler (e.g. 14.2) -------------------------------------------------------------------------------- /sample-build/win-msvc.bat: -------------------------------------------------------------------------------- 1 | @ECHO OFF 2 | 3 | SET CMAKE_PATH=C:\Program Files\CMake\bin 4 | SET MSVC_ROOT=C:\Program Files (x86)\Microsoft Visual Studio\2019\Community 5 | 6 | SET FMT_ROOT=%cd%\deps\fmt 7 | SET BOOST_ROOT=%cd%\deps\root-msvc-14.2-x86_64 8 | 9 | SET BUILD_TYPE=Release 10 | 11 | SET MSVC_COMPILER=v142 12 | SET COMPILER_VERSION=14.2 13 | 14 | SET MSVC_BUILD_ARCH=x64 15 | SET MSVC_ARCH=x64 16 | SET MSVC_TOOLSET="%MSVC_COMPILER%,host=x64" 17 | 18 | CALL "%MSVC_ROOT%\VC\Auxiliary\Build\vcvarsall.bat" %MSVC_ARCH% -vcvars_ver=%COMPILER_VERSION% 19 | 20 | SET PATH=%PATH%;%CMAKE_PATH% 21 | 22 | SET SRC_DIR=%cd%\cpp-validator 23 | SET INSTALL_DIR=%cd%\build\cpp-validator\install 24 | SET BUILD_DIR=%cd%\build\cpp-validator\build 25 | 26 | IF EXIST %BUILD_DIR% rmdir /Q /S %BUILD_DIR% 27 | 28 | SET BASE_DIR=%cd% 29 | 30 | mkdir %BUILD_DIR% 31 | cd %BUILD_DIR% 32 | 33 | cmake -A %MSVC_BUILD_ARCH% -T %MSVC_TOOLSET% ^ 34 | -DCMAKE_INSTALL_PREFIX=%INSTALL_DIR% ^ 35 | -DVALIDATOR_WITH_TESTS=On ^ 36 | -DVALIDATOR_WITH_EXAMPLES=On ^ 37 | %SRC_DIR% 38 | 39 | cmake --build . --config %BUILD_TYPE% -- /m:1 /p:UseMultiToolTask=true /p:MultiProcMaxCount=8 /fileLogger 40 | 41 | SET PATH=%PATH%;%BOOST_ROOT%\lib 42 | ctest -VV -C %BUILD_TYPE% 43 | 44 | cd %BASE_DIR% 45 | -------------------------------------------------------------------------------- /test/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | PROJECT(hatnvalidator-test) 2 | 3 | SET (Boost_USE_STATIC_LIBS OFF CACHE BOOL "Boost static libs") 4 | 5 | FIND_PACKAGE(Boost 1.65 COMPONENTS regex unit_test_framework REQUIRED) 6 | 7 | SET(SOURCES 8 | ${CMAKE_CURRENT_SOURCE_DIR}/main.cpp 9 | ) 10 | 11 | ADD_EXECUTABLE(${PROJECT_NAME} ${SOURCES}) 12 | 13 | SET (VALIDATOR_TEST_SRC ${CMAKE_CURRENT_SOURCE_DIR}) 14 | 15 | INCLUDE(${CMAKE_CURRENT_SOURCE_DIR}/test.cmake) 16 | 17 | TARGET_LINK_LIBRARIES(${PROJECT_NAME} hatnvalidator ${Boost_LIBRARIES}) 18 | 19 | IF (MSVC) 20 | SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /bigobj") 21 | ENDIF() 22 | 23 | ENABLE_TESTING() 24 | ADD_TEST(${PROJECT_NAME} ${PROJECT_NAME} --log_level=test_suite) 25 | -------------------------------------------------------------------------------- /test/main.cpp: -------------------------------------------------------------------------------- 1 | #define BOOST_TEST_MODULE HatnLibsTest 2 | #include 3 | -------------------------------------------------------------------------------- /test/test.cmake: -------------------------------------------------------------------------------- 1 | SET (VALIDATOR_TEST_SOURCES 2 | ${VALIDATOR_TEST_SRC}/testvalidator.cpp 3 | ${VALIDATOR_TEST_SRC}/testvalidatorimpl.cpp 4 | ${VALIDATOR_TEST_SRC}/testreporter.cpp 5 | ${VALIDATOR_TEST_SRC}/testreporting.cpp 6 | ${VALIDATOR_TEST_SRC}/testallanyreport.cpp 7 | ${VALIDATOR_TEST_SRC}/testreportinghints.cpp 8 | ${VALIDATOR_TEST_SRC}/testnomemberreporting.cpp 9 | ${VALIDATOR_TEST_SRC}/testtranslator.cpp 10 | ${VALIDATOR_TEST_SRC}/testfmtformatter.cpp 11 | ${VALIDATOR_TEST_SRC}/teststdformatter.cpp 12 | ${VALIDATOR_TEST_SRC}/teststrings.cpp 13 | ${VALIDATOR_TEST_SRC}/testformatter.cpp 14 | ${VALIDATOR_TEST_SRC}/testtranslator_ru.cpp 15 | ${VALIDATOR_TEST_SRC}/testlexicographical.cpp 16 | ${VALIDATOR_TEST_SRC}/testoperatorin.cpp 17 | ${VALIDATOR_TEST_SRC}/testregex.cpp 18 | ${VALIDATOR_TEST_SRC}/teststrnumbers.cpp 19 | ${VALIDATOR_TEST_SRC}/testvalidatoronheap.cpp 20 | ${VALIDATOR_TEST_SRC}/testinvokeandor.cpp 21 | ${VALIDATOR_TEST_SRC}/testprevalidation.cpp 22 | ${VALIDATOR_TEST_SRC}/testvalidate.cpp 23 | ${VALIDATOR_TEST_SRC}/testsetvalidated.cpp 24 | ${VALIDATOR_TEST_SRC}/testunsetvalidated.cpp 25 | ${VALIDATOR_TEST_SRC}/testresizevalidated.cpp 26 | ${VALIDATOR_TEST_SRC}/testclearvalidated.cpp 27 | ${VALIDATOR_TEST_SRC}/testnestedallany.cpp 28 | ${VALIDATOR_TEST_SRC}/testpartialpaths.cpp 29 | ${VALIDATOR_TEST_SRC}/testnestedvalidators.cpp 30 | ${VALIDATOR_TEST_SRC}/testvariadicproperty.cpp 31 | ${VALIDATOR_TEST_SRC}/testoperatorexists.cpp 32 | ${VALIDATOR_TEST_SRC}/testheterogeneouscontainers.cpp 33 | ${VALIDATOR_TEST_SRC}/testvaluetransformer.cpp 34 | ${VALIDATOR_TEST_SRC}/testtree.cpp 35 | ${VALIDATOR_TEST_SRC}/testpointers.cpp 36 | ) 37 | 38 | IF (BUILD_VALIDATOR_HABR_EXAMPLES) 39 | ADD_COMPILE_DEFINITIONS(-DBUILD_HABR_EXAMPLES) 40 | SET(VALIDATOR_TEST_SOURCES ${VALIDATOR_TEST_SOURCES} ${VALIDATOR_TEST_SRC}/testhabrexamples_ru.cpp) 41 | ENDIF() 42 | 43 | IF (HATN_VALIDATOR_SRC) 44 | SET(TEST_SOURCES ${VALIDATOR_TEST_SOURCES}) 45 | SET(HATN_TEST_THREAD_SOURCES "") 46 | ADD_HATN_CTESTS(validator) 47 | ELSE() 48 | TARGET_SOURCES(${PROJECT_NAME} PRIVATE ${VALIDATOR_TEST_SOURCES}) 49 | ENDIF() 50 | 51 | IF (MINGW) 52 | # Fix string table overflow when compiling in debug mode 53 | SET_SOURCE_FILES_PROPERTIES(${VALIDATOR_TEST_SOURCES} PROPERTIES COMPILE_FLAGS -Og) 54 | ENDIF (MINGW) 55 | 56 | FUNCTION(TestValidator) 57 | ENDFUNCTION(TestValidator) 58 | -------------------------------------------------------------------------------- /test/teststdformatter.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include 4 | #ifdef HATN_VALIDATOR_FMT 5 | #undef HATN_VALIDATOR_FMT 6 | #endif 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | using namespace HATN_VALIDATOR_NAMESPACE; 13 | 14 | BOOST_AUTO_TEST_SUITE(TestStdFormatter) 15 | 16 | #define HATN_VALIDATOR_TEST_FORMATTER 17 | #include "testformatter.cpp" 18 | 19 | namespace 20 | { 21 | auto make_backend_formatter(std::string& dst) 22 | { 23 | return detail::std_backend_formatter{dst}; 24 | } 25 | } 26 | 27 | BOOST_AUTO_TEST_CASE(CheckStdPropertyFlag) 28 | { 29 | checkPropertyFlag(make_backend_formatter); 30 | } 31 | 32 | BOOST_AUTO_TEST_CASE(CheckStdOrderAndPresentation) 33 | { 34 | checkOrderAndPresentation(make_backend_formatter); 35 | } 36 | 37 | BOOST_AUTO_TEST_CASE(CheckStdDefaultFormatter) 38 | { 39 | checkDefaultFormatter(make_backend_formatter); 40 | } 41 | 42 | BOOST_AUTO_TEST_CASE(CheckStdFormatterFromStrings) 43 | { 44 | checkFormatterFromStrings(make_backend_formatter); 45 | } 46 | 47 | BOOST_AUTO_TEST_CASE(CheckFmtFormatterFromTranslator) 48 | { 49 | checkFormatterFromTranslator(make_backend_formatter); 50 | } 51 | 52 | BOOST_AUTO_TEST_CASE(CheckFmtFormatterFromTranslatorRepository) 53 | { 54 | checkFormatterFromTranslatorRepository(make_backend_formatter); 55 | } 56 | 57 | BOOST_AUTO_TEST_CASE(CheckStdFormatterFromMemberNames) 58 | { 59 | checkFormatterFromMemberNames(make_backend_formatter); 60 | } 61 | 62 | BOOST_AUTO_TEST_CASE(CheckStdFormatterFromMemberNamesAndOperands) 63 | { 64 | checkFormatterFromMemberNamesAndOperands(make_backend_formatter); 65 | } 66 | 67 | BOOST_AUTO_TEST_CASE(CheckStdFormatterWithRefs) 68 | { 69 | checkFormatterWithRefs(make_backend_formatter); 70 | } 71 | 72 | BOOST_AUTO_TEST_CASE(CheckStdFormatterWithRvals) 73 | { 74 | checkFormatterWithRvals(make_backend_formatter); 75 | } 76 | 77 | BOOST_AUTO_TEST_SUITE_END() 78 | -------------------------------------------------------------------------------- /test/testunsetvalidated.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include 5 | 6 | #include 7 | #include 8 | 9 | using namespace HATN_VALIDATOR_NAMESPACE; 10 | 11 | BOOST_AUTO_TEST_SUITE(TestPrevalidation) 12 | 13 | BOOST_AUTO_TEST_CASE(CheckUnsetValidated) 14 | { 15 | error_report err; 16 | 17 | auto v1=validator( 18 | _["field1"](exists,true), 19 | _["field1"](eq,100) 20 | ); 21 | std::map m1{ 22 | {"field1","value1"}, 23 | {"field2","value2"}, 24 | {"field3","value3"} 25 | }; 26 | 27 | unset_validated(m1,_["field1"],v1,err); 28 | BOOST_CHECK(err); 29 | BOOST_CHECK_EQUAL(err.message(),std::string("field1 must exist")); 30 | BOOST_CHECK(m1.find("field1")!=m1.end()); 31 | 32 | BOOST_CHECK_THROW(unset_validated(m1,_["field1"],v1),validation_error); 33 | try 34 | { 35 | unset_validated(m1,_["field1"],v1); 36 | } 37 | catch (const validation_error& e) 38 | { 39 | BOOST_CHECK_EQUAL(e.what(),"field1 must exist"); 40 | } 41 | BOOST_CHECK(m1.find("field1")!=m1.end()); 42 | 43 | unset_validated(m1,_["field2"],v1,err); 44 | BOOST_CHECK(!err); 45 | BOOST_CHECK(m1.find("field2")==m1.end()); 46 | 47 | BOOST_CHECK_NO_THROW(unset_validated(m1,_["field3"],v1)); 48 | BOOST_CHECK(m1.find("field3")==m1.end()); 49 | 50 | auto v2=validator( 51 | _["field1"](contains,"value1"), 52 | _["field1"](size(gte,3)) 53 | ); 54 | std::map> m2{ 55 | {"field1",{{"value1","content1"},{"value2","content2"},{"value3","content3"}}} 56 | }; 57 | unset_validated(m2,_["field1"]["value1"],v2,err); 58 | BOOST_CHECK(err); 59 | BOOST_CHECK_EQUAL(err.message(),std::string("field1 must contain value1")); 60 | unset_validated(m2,_["field1"]["value2"],v2,err); 61 | BOOST_CHECK(!err); 62 | BOOST_CHECK_EQUAL(err.message(),std::string("")); 63 | 64 | auto v3=validator( 65 | _["field1"](ANY(contains,"content1")) 66 | ); 67 | std::map>> m3{ 68 | {"field1",{{"value1",{"content1"}},{"value2",{"content2"}},{"value3",{"content3"}}}} 69 | }; 70 | auto& s3=m3["field1"]["value1"]; 71 | unset_validated(m3,_["field1"]["value1"]["content1"],strict_any(v3),err); 72 | BOOST_CHECK(err); 73 | BOOST_CHECK_EQUAL(err.message(),std::string("at least one element of field1 must contain content1")); 74 | BOOST_CHECK(s3.find("content1")!=s3.end()); 75 | 76 | unset_validated(m3,_["field1"]["value1"]["content1"],v3,err); 77 | BOOST_CHECK(!err); 78 | BOOST_CHECK(s3.find("content1")==s3.end()); 79 | } 80 | 81 | BOOST_AUTO_TEST_SUITE_END() 82 | -------------------------------------------------------------------------------- /test/testvalidate.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include 4 | #include 5 | 6 | using namespace HATN_VALIDATOR_NAMESPACE; 7 | 8 | BOOST_AUTO_TEST_SUITE(TestValidate) 9 | 10 | BOOST_AUTO_TEST_CASE(CheckValidateError) 11 | { 12 | auto v=validator(gte,100); 13 | 14 | error err; 15 | 16 | validate(1000,v,err); 17 | BOOST_CHECK(!err); 18 | 19 | validate(50,v,err); 20 | BOOST_CHECK(err); 21 | } 22 | 23 | BOOST_AUTO_TEST_CASE(CheckValidateReport) 24 | { 25 | auto v=validator(gte,100); 26 | 27 | error_report err; 28 | 29 | validate(1000,v,err); 30 | BOOST_CHECK(!err); 31 | 32 | validate(50,v,err); 33 | BOOST_CHECK(err); 34 | BOOST_CHECK_EQUAL(err.message(),"must be greater than or equal to 100"); 35 | } 36 | 37 | BOOST_AUTO_TEST_CASE(CheckValidateThrow) 38 | { 39 | auto v=validator(lte,100); 40 | 41 | BOOST_CHECK_THROW( 42 | validate(1000,v), 43 | validation_error 44 | ); 45 | 46 | BOOST_CHECK_NO_THROW( 47 | validate(50,v) 48 | ); 49 | 50 | try 51 | { 52 | validate(1000,v); 53 | } 54 | catch (const validation_error& err) 55 | { 56 | BOOST_CHECK_EQUAL(err.what(),"must be less than or equal to 100"); 57 | } 58 | } 59 | 60 | BOOST_AUTO_TEST_CASE(CheckPreValidateError) 61 | { 62 | auto v=validator( 63 | _["field1"](gte,100) 64 | ); 65 | 66 | error_report err; 67 | 68 | validate(_["field1"],1000,v,err); 69 | BOOST_CHECK(!err); 70 | 71 | validate(_["field1"],50,v,err); 72 | BOOST_CHECK(err); 73 | BOOST_CHECK_EQUAL(err.message(),"field1 must be greater than or equal to 100"); 74 | } 75 | 76 | BOOST_AUTO_TEST_CASE(CheckPreValidateThrow) 77 | { 78 | auto v=validator( 79 | _["field1"](gte,100) 80 | ); 81 | 82 | BOOST_CHECK_NO_THROW(validate(_["field1"],1000,v)); 83 | 84 | BOOST_CHECK_THROW(validate(_["field1"],50,v),validation_error); 85 | 86 | try 87 | { 88 | validate(_["field1"],50,v); 89 | } 90 | catch (const validation_error& err) 91 | { 92 | BOOST_CHECK_EQUAL(err.what(),"field1 must be greater than or equal to 100"); 93 | } 94 | } 95 | 96 | BOOST_AUTO_TEST_SUITE_END() 97 | --------------------------------------------------------------------------------