| /* |
| * Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You 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. |
| */ |
| |
| #include "ignite_runner.h" |
| #include "test_utils.h" |
| |
| #include <ignite/client/ignite_client.h> |
| #include "ignite/common/detail/utils.h" |
| |
| #include <filesystem> |
| #include <functional> |
| #include <iostream> |
| #include <thread> |
| #include <random> |
| |
| namespace ignite { |
| |
| |
| /** |
| * Checks if the path looks like binary release home directory. |
| * Internally checks for presence of core library. |
| * @return @c true if the path looks like binary release home directory. |
| */ |
| bool looks_like_binary_release_home(const std::filesystem::path &path) { |
| std::filesystem::path core_lib_path = path / "libs"; |
| if (!is_directory(core_lib_path)) |
| return false; |
| |
| auto iter = std::filesystem::directory_iterator{core_lib_path}; |
| return std::any_of(iter, std::filesystem::end(iter), [](auto entry) { |
| const std::filesystem::path &entry_path = entry.path(); |
| if (entry_path.extension() != "jar") |
| return false; |
| |
| std::string stem = entry_path.stem().string(); |
| return stem.find("ignite-core") == 0; |
| }); |
| } |
| |
| /** |
| * Checks if the path looks like source release home directory. |
| * Internally checks for presence of core source directory. |
| * @return @c true if the path looks like binary release home directory. |
| */ |
| bool looks_like_source_release_home(const std::filesystem::path &path) { |
| std::filesystem::path core_source_path = |
| path / "modules" / "core" / "src" / "main" / "java" / "org" / "apache" / "ignite"; |
| |
| return std::filesystem::is_directory(core_source_path); |
| } |
| |
| std::string resolve_ignite_home(const std::string &path) { |
| std::error_code error; |
| |
| std::filesystem::path home = std::filesystem::canonical(path, error); |
| if (!error && std::filesystem::is_directory(path)) |
| return home.string(); |
| |
| auto env = detail::get_env("IGNITE_HOME"); |
| if (env) { |
| home = std::filesystem::canonical(env.value(), error); |
| if (!error && std::filesystem::is_directory(home)) |
| return home.string(); |
| } |
| |
| home = std::filesystem::current_path(); |
| while (!home.empty() && home.has_relative_path()) { |
| if (looks_like_binary_release_home(home) || looks_like_source_release_home(home)) |
| return home.string(); |
| |
| home = home.parent_path(); |
| } |
| return home.string(); |
| } |
| |
| std::filesystem::path resolve_test_dir() { |
| auto home = resolve_ignite_home(); |
| if (home.empty()) |
| throw ignite_error("Can not resolve Ignite Home"); |
| |
| std::filesystem::path home_path(home); |
| auto test_path = home_path / "modules" / "platforms" / "cpp" / "tests"; |
| if (std::filesystem::is_directory(test_path)) |
| return test_path; |
| |
| throw ignite_error("Can not find a 'tests' directory in the current Ignite Home: " + home); |
| } |
| |
| std::filesystem::path resolve_temp_dir(std::string_view subDir, std::string_view prefix) { |
| std::random_device rd; |
| std::mt19937 gen(rd()); |
| std::uniform_int_distribution<> dis(0, 15); |
| |
| std::stringstream ss; |
| |
| if (!prefix.empty()) { |
| ss << prefix << "_"; |
| } |
| |
| |
| for (int i = 0; i < 16; ++i) { |
| int num = dis(gen); |
| |
| if (num <= 9) { |
| ss << num; |
| } else { |
| ss << static_cast<char>('a' + (num - 10)); |
| } |
| } |
| |
| auto path = std::filesystem::temp_directory_path(); |
| |
| if (!subDir.empty()) { |
| path /= subDir; |
| } |
| |
| return path / ss.str(); |
| } |
| |
| bool check_test_node_connectable(std::chrono::seconds timeout) { |
| try { |
| ensure_node_connectable(timeout); |
| return true; |
| } catch (...) { |
| return false; |
| } |
| } |
| |
| void ensure_node_connectable(std::chrono::seconds timeout) { |
| for (auto &addr : ignite_runner::get_node_addrs()) { |
| auto client = ignite_client::start({addr}, timeout); |
| } |
| } |
| |
| bool wait_for_condition(std::chrono::seconds timeout, const std::function<bool()> &predicate) { |
| auto start_time = std::chrono::steady_clock::now(); |
| do { |
| bool success; |
| try { |
| success = predicate(); |
| } catch (...) { |
| success = false; |
| } |
| |
| if (success) |
| return true; |
| |
| std::this_thread::sleep_for(std::chrono::milliseconds(300)); |
| } while ((std::chrono::steady_clock::now() - start_time) < timeout); |
| return false; |
| } |
| |
| } // namespace ignite |