InstallCommand.cpp (6886B)
1 // Copyright (c) Microsoft Corporation. 2 // Licensed under the MIT License. 3 #include "pch.h" 4 #include "AppInstallerRuntime.h" 5 #include "CheckpointManager.h" 6 #include "InstallCommand.h" 7 #include "Workflows/CompletionFlow.h" 8 #include "Workflows/DownloadFlow.h" 9 #include "Workflows/InstallFlow.h" 10 #include "Workflows/UpdateFlow.h" 11 #include "Workflows/MultiQueryFlow.h" 12 #include "Workflows/ResumeFlow.h" 13 #include "Workflows/WorkflowBase.h" 14 #include "Resources.h" 15 16 namespace AppInstaller::CLI 17 { 18 using namespace AppInstaller::CLI::Execution; 19 using namespace AppInstaller::CLI::Workflow; 20 using namespace AppInstaller::Manifest; 21 using namespace AppInstaller::Utility::literals; 22 23 std::vector<Argument> InstallCommand::GetArguments() const 24 { 25 return { 26 Argument::ForType(Args::Type::MultiQuery), 27 Argument::ForType(Args::Type::Manifest), 28 Argument::ForType(Args::Type::Id), 29 Argument::ForType(Args::Type::Name), 30 Argument::ForType(Args::Type::Moniker), 31 Argument::ForType(Args::Type::Version), 32 Argument::ForType(Args::Type::Channel), 33 Argument::ForType(Args::Type::Source), 34 Argument{ Args::Type::InstallScope, Resource::String::InstallScopeDescription, ArgumentType::Standard, Argument::Visibility::Help }, 35 Argument::ForType(Args::Type::InstallArchitecture), 36 Argument::ForType(Args::Type::InstallerType), 37 Argument::ForType(Args::Type::Exact), 38 Argument::ForType(Args::Type::Interactive), 39 Argument::ForType(Args::Type::Silent), 40 Argument::ForType(Args::Type::Locale), 41 Argument::ForType(Args::Type::Log), 42 Argument::ForType(Args::Type::CustomSwitches), 43 Argument::ForType(Args::Type::Override), 44 Argument::ForType(Args::Type::InstallLocation), 45 Argument::ForType(Args::Type::HashOverride), 46 Argument::ForType(Args::Type::AllowReboot), 47 Argument::ForType(Args::Type::SkipDependencies), 48 Argument::ForType(Args::Type::IgnoreLocalArchiveMalwareScan), 49 Argument::ForType(Args::Type::DependencySource), 50 Argument::ForType(Args::Type::AcceptPackageAgreements), 51 Argument::ForType(Args::Type::NoUpgrade), 52 Argument::ForType(Args::Type::CustomHeader), 53 Argument::ForType(Args::Type::AuthenticationMode), 54 Argument::ForType(Args::Type::AuthenticationAccount), 55 Argument::ForType(Args::Type::AcceptSourceAgreements), 56 Argument::ForType(Args::Type::Rename), 57 Argument::ForType(Args::Type::UninstallPrevious), 58 Argument::ForType(Args::Type::Force), 59 Argument{ Args::Type::IncludeUnknown, Resource::String::IncludeUnknownArgumentDescription, ArgumentType::Flag, Argument::Visibility::Hidden}, 60 }; 61 } 62 63 Resource::LocString InstallCommand::ShortDescription() const 64 { 65 return { Resource::String::InstallCommandShortDescription }; 66 } 67 68 Resource::LocString InstallCommand::LongDescription() const 69 { 70 return { Resource::String::InstallCommandLongDescription }; 71 } 72 73 void InstallCommand::Complete(Context& context, Args::Type valueType) const 74 { 75 switch (valueType) 76 { 77 case Args::Type::MultiQuery: 78 case Args::Type::Manifest: 79 case Args::Type::Id: 80 case Args::Type::Name: 81 case Args::Type::Moniker: 82 case Args::Type::Version: 83 case Args::Type::Channel: 84 case Args::Type::Source: 85 context << 86 Workflow::CompleteWithSingleSemanticsForValue(valueType); 87 break; 88 case Args::Type::InstallArchitecture: 89 case Args::Type::Locale: 90 // May well move to CompleteWithSingleSemanticsForValue, 91 // but for now output nothing. 92 context << 93 Workflow::CompleteWithEmptySet; 94 break; 95 case Args::Type::Log: 96 case Args::Type::InstallLocation: 97 // Intentionally output nothing to allow pass through to filesystem. 98 break; 99 } 100 } 101 102 Utility::LocIndView InstallCommand::HelpLink() const 103 { 104 return "https://aka.ms/winget-command-install"_liv; 105 } 106 107 void InstallCommand::ValidateArgumentsInternal(Args& execArgs) const 108 { 109 Argument::ValidateCommonArguments(execArgs); 110 } 111 112 void InstallCommand::Resume(Context& context) const 113 { 114 // TODO: Load context data from checkpoint for install command. 115 ExecuteInternal(context); 116 } 117 118 void InstallCommand::ExecuteInternal(Context& context) const 119 { 120 context.SetFlags(ContextFlag::ShowSearchResultsOnPartialFailure); 121 122 context << InitializeInstallerDownloadAuthenticatorsMap; 123 124 if (context.Args.Contains(Execution::Args::Type::Manifest)) 125 { 126 context << 127 ReportExecutionStage(ExecutionStage::Discovery) << 128 GetManifestFromArg << 129 SelectInstaller << 130 EnsureApplicableInstaller << 131 Checkpoint("PreInstallCheckpoint", {}) << // TODO: Capture context data 132 InstallSinglePackage; 133 } 134 else 135 { 136 context << 137 ReportExecutionStage(ExecutionStage::Discovery) << 138 OpenSource(); 139 140 if (!context.Args.Contains(Execution::Args::Type::Force)) 141 { 142 context << 143 OpenCompositeSource(DetermineInstalledSource(context), false, Repository::CompositeSearchBehavior::AvailablePackages); 144 } 145 146 if (context.Args.Contains(Execution::Args::Type::MultiQuery)) 147 { 148 ProcessMultiplePackages::Flags flags = ProcessMultiplePackages::Flags::None; 149 if (Settings::User().Get<Settings::Setting::InstallSkipDependencies>() || context.Args.Contains(Execution::Args::Type::SkipDependencies)) 150 { 151 flags = ProcessMultiplePackages::Flags::IgnoreDependencies; 152 } 153 154 context << 155 GetMultiSearchRequests << 156 SearchSubContextsForSingle() << 157 ReportExecutionStage(ExecutionStage::Execution) << 158 ProcessMultiplePackages(Resource::String::PackageRequiresDependencies, APPINSTALLER_CLI_ERROR_MULTIPLE_INSTALL_FAILED, flags); 159 } 160 else 161 { 162 context << 163 Checkpoint("PreInstallCheckpoint", {}) << // TODO: Capture context data 164 InstallOrUpgradeSinglePackage(OperationType::Install); 165 } 166 } 167 } 168 }