Added basic framework for creating cxx20 test cases

This commit is contained in:
Bartek Kryza
2023-02-15 22:13:38 +01:00
parent 6be07a7dfa
commit 040403382a
8 changed files with 153 additions and 31 deletions

View File

@@ -27,6 +27,31 @@
#include <type_traits>
#include <vector>
#define LOG_ERROR(fmt__, ...) \
spdlog::get("console")->error( \
fmt::runtime(std::string("[{}:{}] ") + fmt__), FILENAME_, __LINE__, \
##__VA_ARGS__)
#define LOG_WARN(fmt__, ...) \
spdlog::get("console")->warn( \
fmt::runtime(std::string("[{}:{}] ") + fmt__), FILENAME_, __LINE__, \
##__VA_ARGS__)
#define LOG_INFO(fmt__, ...) \
spdlog::get("console")->info( \
fmt::runtime(std::string("[{}:{}] ") + fmt__), FILENAME_, __LINE__, \
##__VA_ARGS__)
#define LOG_DBG(fmt__, ...) \
spdlog::get("console")->debug( \
fmt::runtime(std::string("[{}:{}] ") + fmt__), FILENAME_, __LINE__, \
##__VA_ARGS__)
#define LOG_TRACE(fmt__, ...) \
spdlog::get("console")->trace( \
fmt::runtime(std::string("[{}:{}] ") + fmt__), FILENAME_, __LINE__, \
##__VA_ARGS__)
namespace clanguml::util {
std::string ltrim(const std::string &s);
@@ -36,26 +61,6 @@ std::string trim(const std::string &s);
#define FILENAME_ \
(strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__)
#define LOG_ERROR(fmt__, ...) \
spdlog::get("console")->error( \
std::string("[{}:{}] ") + fmt__, FILENAME_, __LINE__, ##__VA_ARGS__)
#define LOG_WARN(fmt__, ...) \
spdlog::get("console")->warn( \
std::string("[{}:{}] ") + fmt__, FILENAME_, __LINE__, ##__VA_ARGS__)
#define LOG_INFO(fmt__, ...) \
spdlog::get("console")->info( \
std::string("[{}:{}] ") + fmt__, FILENAME_, __LINE__, ##__VA_ARGS__)
#define LOG_DBG(fmt__, ...) \
spdlog::get("console")->debug( \
std::string("[{}:{}] ") + fmt__, FILENAME_, __LINE__, ##__VA_ARGS__)
#define LOG_TRACE(fmt__, ...) \
spdlog::get("console")->trace( \
std::string("[{}:{}] ") + fmt__, FILENAME_, __LINE__, ##__VA_ARGS__)
/**
* @brief Setup spdlog logger.
*

View File

@@ -3,6 +3,8 @@ file(GLOB_RECURSE TEST_CASE_SOURCES t*/*.cc t*/*.c t*/src/*.c)
file(GLOB_RECURSE TEST_CASE_CONFIGS t*/.clang-uml)
file(GLOB_RECURSE TEST_CONFIG_YMLS test_config_data/*.yml)
set(TEST_CASES_REQUIRING_CXX20 t00056)
set(CLANG_UML_TEST_LIBRARIES
clang-umllib
${YAML_CPP_LIBRARIES}
@@ -13,6 +15,23 @@ if(MSVC)
list(APPEND CLANG_UML_TEST_LIBRARIES "Version.lib")
endif(MSVC)
list(FIND CMAKE_CXX_COMPILE_FEATURES cxx_std_20 SUPPORTS_CXX_STD_20)
if(SUPPORTS_CXX_STD_20 EQUAL -1
OR ${LLVM_PACKAGE_VERSION} VERSION_LESS "15.0")
set(ENABLE_CXX_STD_20_TEST_CASES 0)
foreach(CXX20_TC ${TEST_CASES_REQUIRING_CXX20})
list(FILTER TEST_CASE_SOURCES
EXCLUDE
REGEX ".*${CXX20_TC}.*")
list(FILTER TEST_CASE_CONFIGS
EXCLUDE
REGEX ".*${CXX20_TC}.*")
endforeach()
else()
set(ENABLE_CXX_STD_20_TEST_CASES 1)
endif()
set(TEST_CASES
test_util
test_model
@@ -27,11 +46,14 @@ foreach(TEST_NAME ${TEST_CASES})
${TEST_NAME}.cc
$<$<STREQUAL:${TEST_NAME},test_cases>:${TEST_CASE_SOURCES}>
catch.h)
target_compile_features(${TEST_NAME} PRIVATE cxx_std_17)
target_compile_features(${TEST_NAME} PRIVATE
$<IF:${ENABLE_CXX_STD_20_TEST_CASES},cxx_std_20,cxx_std_17>)
target_compile_definitions(${TEST_NAME} PRIVATE
$<$<EQUAL:${ENABLE_CXX_STD_20_TEST_CASES},1>:ENABLE_CXX_STD_20_TEST_CASES>)
target_compile_options(${TEST_NAME} PRIVATE
$<$<OR:$<CXX_COMPILER_ID:Clang>,$<CXX_COMPILER_ID:GNU>>:
-Wno-unused-parameter -Wno-unused-private-field -Wno-unused-variable
-Wno-attributes -Wno-nonnull>
-Wno-attributes -Wno-nonnull -Wno-deprecated-enum-enum-conversion>
$<$<CXX_COMPILER_ID:MSVC>:/MP /W1 /bigobj /wd4624>)
target_link_libraries(${TEST_NAME} PRIVATE ${CLANG_UML_TEST_LIBRARIES})
endforeach()

12
tests/t00056/.clang-uml Normal file
View File

@@ -0,0 +1,12 @@
compilation_database_dir: ..
output_directory: puml
diagrams:
t00056_class:
type: class
glob:
- ../../tests/t00056/t00056.cc
include:
namespaces:
- clanguml::t00056
using_namespace:
- clanguml::t00056

10
tests/t00056/t00056.cc Normal file
View File

@@ -0,0 +1,10 @@
namespace clanguml {
namespace t00056 {
template <typename T>
concept MaxFourBytes = sizeof(T) <= 4;
template <MaxFourBytes T> struct A {
T a;
};
}
}

66
tests/t00056/test_case.h Normal file
View File

@@ -0,0 +1,66 @@
/**
* tests/t00056/test_case.h
*
* Copyright (c) 2021-2023 Bartek Kryza <bkryza@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
TEST_CASE("t00056", "[test-case][class]")
{
auto [config, db] = load_config("t00056");
auto diagram = config.diagrams["t00056_class"];
REQUIRE(diagram->name == "t00056_class");
auto model = generate_class_diagram(*db, diagram);
REQUIRE(model->name() == "t00056_class");
auto puml = generate_class_puml(diagram, *model);
AliasMatcher _A(puml);
REQUIRE_THAT(puml, StartsWith("@startuml"));
REQUIRE_THAT(puml, EndsWith("@enduml\n"));
// Check if all classes exist
// REQUIRE_THAT(puml, IsClass(_A("A")));
// Check if class templates exist
// REQUIRE_THAT(puml, IsClassTemplate("A", "T,P,CMP,int N"));
// Check if all enums exist
// REQUIRE_THAT(puml, IsEnum(_A("Lights")));
// Check if all inner classes exist
// REQUIRE_THAT(puml, IsInnerClass(_A("A"), _A("AA")));
// Check if all inheritance relationships exist
// REQUIRE_THAT(puml, IsBaseClass(_A("Base"), _A("Child")));
// Check if all methods exist
// REQUIRE_THAT(puml, (IsMethod<Public, Const>("foo")));
// Check if all fields exist
// REQUIRE_THAT(puml, (IsField<Private>("private_member", "int")));
// Check if all relationships exist
// REQUIRE_THAT(puml, IsAssociation(_A("D"), _A("A"), "-as"));
// REQUIRE_THAT(puml, IsDependency(_A("R"), _A("B")));
// REQUIRE_THAT(puml, IsAggregation(_A("R"), _A("D")));
// REQUIRE_THAT(puml, IsComposition(_A("R"), _A("D")));
// REQUIRE_THAT(puml, IsInstantiation(_A("ABCD::F<T>"), _A("F<int>")));
save_puml(config.output_directory() + "/" + diagram->name + ".puml", puml);
}

View File

@@ -34,7 +34,7 @@ template <typename T> struct BB<T, std::string> {
void bb1(T t, std::string f) { aa_->aa2(t); }
void bb2(T t, std::string f) { aa_->aa1(t); }
BB<T, std::string>(AA<T> *aa)
BB(AA<T> *aa)
: aa_{aa}
{
}
@@ -46,7 +46,7 @@ template <typename T> struct BB<T, float> {
void bb1(T t, float f) { bb2(t, f); }
void bb2(T t, float f) { aa_.aa2(t); }
BB<T, float>(AA<T> &aa)
BB(AA<T> &aa)
: aa_{aa}
{
}

View File

@@ -255,6 +255,9 @@ using namespace clanguml::test::matchers;
#include "t00053/test_case.h"
#include "t00054/test_case.h"
#include "t00055/test_case.h"
#if defined(ENABLE_CXX_STD_20_TEST_CASES)
#include "t00056/test_case.h"
#endif
#include "t00057/test_case.h"
///
@@ -340,4 +343,4 @@ int main(int argc, char *argv[])
clanguml::util::setup_logging(debug_log ? 3 : 1);
return session.run();
}
}

View File

@@ -334,11 +334,13 @@ ContainsMatcher IsAssociation(std::string const &from, std::string const &to,
if (!label.empty()) {
format_string += " : {}";
return ContainsMatcher(CasedString(
fmt::format(format_string, from, to, label), caseSensitivity));
fmt::format(fmt::runtime(format_string), from, to, label),
caseSensitivity));
}
else
return ContainsMatcher(
CasedString(fmt::format(format_string, from, to), caseSensitivity));
CasedString(fmt::format(fmt::runtime(format_string), from, to),
caseSensitivity));
}
ContainsMatcher IsComposition(std::string const &from, std::string const &to,
@@ -357,8 +359,9 @@ ContainsMatcher IsComposition(std::string const &from, std::string const &to,
format_string += " {} : {}";
return ContainsMatcher(CasedString(
fmt::format(format_string, from, to, label), caseSensitivity));
return ContainsMatcher(
CasedString(fmt::format(fmt::runtime(format_string), from, to, label),
caseSensitivity));
}
ContainsMatcher IsAggregation(std::string const &from, std::string const &to,
@@ -377,8 +380,9 @@ ContainsMatcher IsAggregation(std::string const &from, std::string const &to,
format_string += " {} : {}";
return ContainsMatcher(CasedString(
fmt::format(format_string, from, to, label), caseSensitivity));
return ContainsMatcher(
CasedString(fmt::format(fmt::runtime(format_string), from, to, label),
caseSensitivity));
}
ContainsMatcher IsAggregationWithStyle(std::string const &from,