diff options
| author | Leitwolf11 | 2026-11-01 22:58:30 +0300 |
|---|---|---|
| committer | Leitwolf11 | 2026-11-01 22:58:30 +0300 |
| commit | e66db1cf17714be2ebfeab37670ef3d8965fc7cc (patch) | |
| tree | 88a8b55a14e9bc6152608662d062c1624c2863cf /tools/RepositoryReport.cpp | |
| parent | e32c9d107274f42b9cca700475404c80e96533c5 (diff) | |
| download | catch3-e66db1cf17714be2ebfeab37670ef3d8965fc7cc.tar.gz | |
Answer the review of the tools
repo_info starts Git in the checkout with fixed commands, so a shell never
reads a path, reports an unknown state as null rather than clean, and
counts only files it can start. third_party reads every archive before
it changes a file and refuses two modes. version checks that the sources
make a distribution, computes every place before writing any, and
release_notes finds a three-number heading for a version with D = 0.
Diffstat (limited to 'tools/RepositoryReport.cpp')
| -rw-r--r-- | tools/RepositoryReport.cpp | 58 |
1 files changed, 44 insertions, 14 deletions
diff --git a/tools/RepositoryReport.cpp b/tools/RepositoryReport.cpp index 4b2b1502..f985335e 100644 --- a/tools/RepositoryReport.cpp +++ b/tools/RepositoryReport.cpp @@ -10,6 +10,10 @@ #include <string_view> #include <system_error> +#if !defined(_WIN32) +# include <unistd.h> +#endif + #include "tools/Amalgamation.hpp" #include "tools/Repository.hpp" #include "tools/RepositoryReport.hpp" @@ -70,6 +74,22 @@ namespace Progmasoft::Catch3::Tools #endif } + /// Whether `file` can be started, which only POSIX says of a file. + [[nodiscard]] bool + IsProgram(const fs::path &file) + { + std::error_code error; + if (!fs::is_regular_file(file, error)) + { + return false; + } +#if defined(_WIN32) + return true; +#else + return access(file.c_str(), X_OK) == 0; +#endif + } + [[nodiscard]] ToolInfo Find(std::string_view name, std::string_view searchPath) { @@ -92,8 +112,7 @@ namespace Progmasoft::Catch3::Tools const auto file = directory / (std::string{ name } + std::string{ extension }); - std::error_code error; - if (fs::is_regular_file(file, error)) + if (IsProgram(file)) { tool.Path = file.string(); tool.Available = true; @@ -104,13 +123,13 @@ namespace Progmasoft::Catch3::Tools return tool; } - /// What `git <arguments>` writes in `root`, or nothing when it fails. + /// What `git <arguments>` writes in the current directory, or nothing + /// when it fails. A shell reads the command, so it never holds a path. [[nodiscard]] std::optional<std::string> - Git(const fs::path &root, std::string_view arguments) + Git(std::string_view arguments) { - const auto command = "git -C \"" + root.string() + "\" " - + std::string{ arguments } - + std::string{ kNoErrors }; + const auto command + = "git " + std::string{ arguments } + std::string{ kNoErrors }; #if defined(_WIN32) auto *pipe = _popen(command.c_str(), "r"); #else @@ -197,11 +216,12 @@ namespace Progmasoft::Catch3::Tools report.Tools.push_back(Find(name, searchPath)); } - const auto branch = Git(root, "branch --show-current"); - const auto revision = Git(root, "rev-parse HEAD"); - const auto status - = Git(root, "status --porcelain --untracked-files=no"); - if (branch && revision && status) + std::error_code error; + fs::current_path(root, error); + const auto branch = Git("branch --show-current"); + const auto revision = Git("rev-parse HEAD"); + const auto status = Git("status --porcelain --untracked-files=no"); + if (!error && branch && revision && status) { report.Branch = *branch; report.Revision = *revision; @@ -224,7 +244,10 @@ namespace Progmasoft::Catch3::Tools text += "Branch: " + report.Branch + "\n"; text += "Revision: " + report.Revision + "\n"; text += std::string{ "Tracked changes: " } - + (report.Dirty ? "true" : "false") + "\n"; + + (!report.Dirty ? "unknown" + : *report.Dirty ? "true" + : "false") + + "\n"; if (!report.GitError.empty()) { text += report.GitError + "\n"; @@ -254,7 +277,14 @@ namespace Progmasoft::Catch3::Tools AddText(document, root, "engineVersion", report.EngineVersion); AddText(document, root, "branch", report.Branch); AddText(document, root, "revision", report.Revision); - yyjson_mut_obj_add_bool(document, root, "dirty", report.Dirty); + if (report.Dirty) + { + yyjson_mut_obj_add_bool(document, root, "dirty", *report.Dirty); + } + else + { + yyjson_mut_obj_add_null(document, root, "dirty"); + } AddText(document, root, "gitError", report.GitError); auto *tools = yyjson_mut_obj_add_arr(document, root, "tools"); for (const auto &tool : report.Tools) |