Line data Source code
1 : /*! 2 : * \file esys/repo/cli/cmdsync_cli.cpp 3 : * \brief 4 : * 5 : * \cond 6 : * __legal_b__ 7 : * 8 : * Copyright (c) 2020-2023 Michel Gillet 9 : * Distributed under the MIT License. 10 : * (See accompanying file LICENSE.txt or 11 : * copy at https://opensource.org/licenses/MIT) 12 : * 13 : * __legal_e__ 14 : * \endcond 15 : * 16 : */ 17 : 18 : #include "esys/repo/esysrepo_prec.h" 19 : #include "esys/repo/cli/cmdsync.h" 20 : #include "esys/repo/githelper.h" 21 : 22 : #include <esys/md/rend/styled_string.h> 23 : 24 : #include <termcolor/termcolor.hpp> 25 : 26 : #include <boost/filesystem.hpp> 27 : 28 : #include <vector> 29 : 30 : namespace esys::repo::cli 31 : { 32 : 33 : #include "esys/repo/cli/cmdsync_doc.cpp" 34 : 35 21 : CmdSync::CmdSync(AppBase *app) 36 42 : : BaseType(app, "sync", "Update working tree to the latest revision") 37 : { 38 21 : } 39 : 40 21 : CmdSync::~CmdSync() = default; 41 : 42 7 : std::shared_ptr<po::options_description> CmdSync::get_desc() 43 : { 44 7 : auto desc = Cmd::get_desc(); 45 7 : if (desc != nullptr) return desc; 46 : 47 7 : desc = std::make_shared<po::options_description>("Sync options"); 48 : // clang-format off 49 7 : desc->add_options() 50 7 : ("force-sync", po::value<bool>()->default_value(false)->implicit_value(true), 51 : "overwrite an existing git directory if it needs to" 52 : "point to a different object directory. WARNING: this" 53 : "may cause loss of data") 54 7 : ("job,j", po::value<int>()->default_value(1), "projects to fetch simultaneously (default 1)") 55 7 : ("groups,g", po::value<std::string>(), "the groups to synchronize") 56 7 : ("prefer-branch,b", po::value<std::string>(), 57 : "checkout this branch on each project when it exists (else manifest)") 58 7 : ("rev-set", po::value<std::string>(), "native manifest revision-set name") 59 7 : ("alt,a", "use alternative address for git repos") 60 7 : ("multi,m", "use captured branches for changes spanning multiple repositories") 61 7 : ("tui", "fullscreen Compact RepoSync progress dashboard (TTY; requires FTXUI build)") 62 7 : ("tui-demo", "like --tui, plus a timed on-screen Tab hint (also ESYSREPO_TUI_DEMO=1)") 63 7 : ("phase-timing", "log per-repo GitHelper phase timings (ms); overrides ESYSREPO_SYNC_PHASE_TIMING") 64 7 : ("no-phase-timing", "disable phase timing logs even if ESYSREPO_SYNC_PHASE_TIMING is set") 65 7 : ("recurse-submodules", "also sync Git submodules of each project (ADR-0032)") 66 7 : ("no-recurse-submodules", "do not sync Git submodules even if sync-s is set (ADR-0032)") 67 : ; 68 : // clang-format on 69 14 : Cmd::set_desc(desc); 70 7 : return desc; 71 0 : } 72 : 73 13 : int CmdSync::configure_cmd(CmdType &cmd) 74 : { 75 52 : if (get_vm().count("job")) cmd.set_job_count(get_vm()["job"].as<int>()); 76 13 : cmd.set_sub_args(get_sub_args()); 77 26 : if (get_vm().count("groups")) 78 : { 79 0 : std::vector<std::string> groups; 80 : 81 0 : int result = groups_str_to_groups(get_vm()["groups"].as<std::string>(), groups); 82 0 : if (result < 0) 83 : { 84 0 : return -1; 85 : } 86 0 : cmd.set_groups(groups); 87 0 : } 88 30 : if (get_vm().count("prefer-branch")) cmd.set_branch(get_vm()["prefer-branch"].as<std::string>()); 89 39 : auto reject_old_branch = [this](const std::vector<std::string> &args) -> bool { 90 39 : for (const auto &arg : args) 91 : { 92 13 : if (arg == "--branch" || arg.rfind("--branch=", 0) == 0) 93 : { 94 0 : error("sync --branch was renamed to --prefer-branch (ADR-0037); -b is unchanged"); 95 0 : return true; 96 : } 97 : } 98 : return false; 99 13 : }; 100 13 : if (reject_old_branch(get_sub_args()) || reject_old_branch(get_unrecognized())) return -1; 101 30 : if (get_vm().count("rev-set")) cmd.set_rev_set(get_vm()["rev-set"].as<std::string>()); 102 26 : if (get_vm()["force-sync"].as<bool>()) cmd.set_force(true); 103 26 : if (get_vm().count("alt")) cmd.set_alt_address(true); 104 26 : if (get_vm().count("multi")) cmd.set_multi(true); 105 26 : if (get_vm().count("tui")) cmd.set_tui(true); 106 26 : if (get_vm().count("tui-demo")) cmd.set_tui_demo(true); 107 26 : if (get_vm().count("phase-timing")) GitHelper::set_phase_timing(true); 108 26 : if (get_vm().count("no-phase-timing")) GitHelper::set_phase_timing(false); 109 : // Prefer --no-recurse-submodules when both flags are present (safer). 110 26 : if (get_vm().count("no-recurse-submodules")) 111 2 : cmd.set_recurse_submodules(manifest::RecurseSubmodules::No); 112 22 : else if (get_vm().count("recurse-submodules")) 113 1 : cmd.set_recurse_submodules(manifest::RecurseSubmodules::Yes); 114 : 115 : return 0; 116 : } 117 : 118 1 : int CmdSync::print_doc(std::ostream &os) 119 : { 120 1 : os << cmdsync_doc_strings; 121 1 : return 0; 122 : } 123 : 124 : } // namespace esys::repo::cli