Skip to content

Commit 248d4a0

Browse files
yao-msftJohnMcPMS
andauthored
Add api to find unit processors based on search path (#5386)
Added EnvironmentVariables customization support for ProcessExecution. Added ProcessorRunSettings to customize each processor run settings. Currently only used to change path environment variables for processor runs. Added support to find unit processors based on search path. If search paths not provided, the api will list all unit processors that can be found. Added e2e tests. ###### Microsoft Reviewers: [Open in CodeFlow](https://microsoft.github.io/open-pr/?codeflow=https://github.com/microsoft/winget-cli/pull/5386) --------- Co-authored-by: John McPherson <[email protected]>
1 parent ea35028 commit 248d4a0

31 files changed

+902
-61
lines changed

src/AppInstallerCLICore/Commands/DebugCommand.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,10 +104,13 @@ namespace AppInstaller::CLI
104104
OutputProxyStubInterfaceRegistration<winrt::Windows::Foundation::Collections::IIterable<winrt::Microsoft::Management::Configuration::IApplyGroupMemberSettingsResult>>(context);
105105
OutputProxyStubInterfaceRegistration<winrt::Windows::Foundation::Collections::IIterable<winrt::Microsoft::Management::Configuration::ITestSettingsResult>>(context);
106106
OutputProxyStubInterfaceRegistration<winrt::Windows::Foundation::Collections::IIterable<winrt::Microsoft::Management::Configuration::ConfigurationEnvironment>>(context);
107+
OutputProxyStubInterfaceRegistration<winrt::Windows::Foundation::Collections::IIterable<winrt::Microsoft::Management::Configuration::IConfigurationUnitProcessorDetails>>(context);
107108
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IConfigurationUnitProcessorDetails2>(context);
108109
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IGetAllSettingsConfigurationUnitProcessor>(context);
109110
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IGetAllUnitsConfigurationUnitProcessor>(context);
111+
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IFindUnitProcessorsSetProcessor>(context);
110112
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IConfigurationStatics2>(context);
113+
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::IConfigurationStatics3>(context);
111114
OutputProxyStubInterfaceRegistration<winrt::Microsoft::Management::Configuration::SetProcessorFactory::IPwshConfigurationSetProcessorFactoryProperties>(context);
112115

113116
// TODO: Fix the layering inversion created by the COM deployment API (probably in order to operate winget.exe against the COM server).
@@ -135,6 +138,7 @@ namespace AppInstaller::CLI
135138
{
136139
OutputIIDMapping<winrt::Microsoft::Management::Configuration::IConfigurationStatics>(context);
137140
OutputIIDMapping<winrt::Microsoft::Management::Configuration::IConfigurationStatics2>(context);
141+
OutputIIDMapping<winrt::Microsoft::Management::Configuration::IConfigurationStatics3>(context);
138142
}
139143

140144
Resource::LocString DumpErrorResourceCommand::ShortDescription() const

src/AppInstallerCLICore/Commands/TestCommand.cpp

Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
#include "TestCommand.h"
88
#include "AppInstallerRuntime.h"
9+
#include "TableOutput.h"
910
#include "Public/ConfigurationSetProcessorFactoryRemoting.h"
1011
#include "Workflows/ConfigurationFlow.h"
1112
#include <winrt/Microsoft.Management.Configuration.h>
@@ -140,6 +141,80 @@ namespace AppInstaller::CLI
140141
WriteConfigFile;
141142
}
142143
};
144+
145+
void InvokeFindUnitProcessors(Execution::Context& context)
146+
{
147+
auto& configurationContext = context.Get<Execution::Data::ConfigurationContext>();
148+
149+
winrt::Microsoft::Management::Configuration::FindUnitProcessorsOptions findOptions;
150+
151+
if (context.Args.Contains(Execution::Args::Type::InstallLocation))
152+
{
153+
findOptions.SearchPaths(Utility::ConvertToUTF16(context.Args.GetArg(Execution::Args::Type::InstallLocation)));
154+
findOptions.SearchPathsExclusive(true);
155+
findOptions.UnitDetailFlags(winrt::Microsoft::Management::Configuration::ConfigurationUnitDetailFlags::Local);
156+
}
157+
158+
auto result = configurationContext.Processor().FindUnitProcessors(findOptions);
159+
160+
if (result.Size() > 0)
161+
{
162+
Execution::TableOutput<2> table(context.Reporter,
163+
{
164+
"Type"_lis,
165+
"Description"_lis
166+
});
167+
168+
for (const auto& resultUnitProcessor : result)
169+
{
170+
table.OutputLine({
171+
Utility::ConvertToUTF8(resultUnitProcessor.UnitType()),
172+
Utility::ConvertToUTF8(resultUnitProcessor.UnitDescription())
173+
});
174+
}
175+
176+
table.Complete();
177+
}
178+
else
179+
{
180+
context.Reporter.Info() << "No unit processors found."_lis << std::endl;
181+
}
182+
}
183+
184+
// Command to directly invoke find unit processors.
185+
struct TestConfigurationFindUnitProcessorsCommand final : public Command
186+
{
187+
TestConfigurationFindUnitProcessorsCommand(std::string_view parent) : Command("config-find-unit-processors", {}, parent) {}
188+
189+
std::vector<Argument> GetArguments() const override
190+
{
191+
return {
192+
Argument{ Execution::Args::Type::InstallLocation, Resource::String::LocationArgumentDescription },
193+
};
194+
}
195+
196+
Resource::LocString ShortDescription() const override
197+
{
198+
return "Run find unit processors"_lis;
199+
}
200+
201+
Resource::LocString LongDescription() const override
202+
{
203+
return "Runs find unit processors. Search paths could be provided."_lis;
204+
}
205+
206+
protected:
207+
void ExecuteInternal(Execution::Context& context) const override
208+
{
209+
context <<
210+
VerifyIsFullPackage <<
211+
CreateConfigurationProcessorWithoutFactory <<
212+
CreateOrOpenConfigurationSet{ "0.3" } <<
213+
EnsureDSCv3Processor <<
214+
CreateConfigurationProcessor <<
215+
InvokeFindUnitProcessors;
216+
}
217+
};
143218
}
144219

145220
std::vector<std::unique_ptr<Command>> TestCommand::GetCommands() const
@@ -148,6 +223,7 @@ namespace AppInstaller::CLI
148223
{
149224
std::make_unique<TestAppShutdownCommand>(FullName()),
150225
std::make_unique<TestConfigurationExportCommand>(FullName()),
226+
std::make_unique<TestConfigurationFindUnitProcessorsCommand>(FullName()),
151227
});
152228
}
153229

src/AppInstallerCLICore/ConfigurationDynamicRuntimeFactory.cpp

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -155,7 +155,7 @@ namespace AppInstaller::CLI::ConfigurationRemoting
155155
IConfigurationSetProcessorFactory::Diagnostics_revoker DiagnosticsEventRevoker;
156156
};
157157

158-
struct DynamicSetProcessor : winrt::implements<DynamicSetProcessor, IConfigurationSetProcessor>
158+
struct DynamicSetProcessor : winrt::implements<DynamicSetProcessor, IConfigurationSetProcessor, IFindUnitProcessorsSetProcessor>
159159
{
160160
using ProcessorMap = std::map<Security::IntegrityLevel, DynamicProcessorInfo>;
161161

@@ -257,6 +257,21 @@ namespace AppInstaller::CLI::ConfigurationRemoting
257257
return itr->second.Processor.CreateUnitProcessor(unit);
258258
}
259259

260+
Collections::IVector<IConfigurationUnitProcessorDetails> FindUnitProcessors(const FindUnitProcessorsOptions& findOptions)
261+
{
262+
IFindUnitProcessorsSetProcessor findUnitProcessorsSetProcessor;
263+
264+
if (m_setProcessors[m_currentIntegrityLevel].Processor.try_as<IFindUnitProcessorsSetProcessor>(findUnitProcessorsSetProcessor))
265+
{
266+
return findUnitProcessorsSetProcessor.FindUnitProcessors(findOptions);
267+
}
268+
else
269+
{
270+
AICLI_LOG(Config, Error, << "Set Processor does not support FindUnitProcessors operation");
271+
THROW_HR(WINGET_CONFIG_ERROR_NOT_SUPPORTED_BY_PROCESSOR);
272+
}
273+
}
274+
260275
private:
261276
// Converts the string representation of SecurityContext to the target integrity level for this instance
262277
Security::IntegrityLevel SecurityContextToIntegrityLevel(SecurityContext securityContext)

src/AppInstallerCLICore/ExecutionReporter.cpp

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -175,7 +175,6 @@ namespace AppInstaller::CLI::Execution
175175
std::string response;
176176
if (!std::getline(m_in, response))
177177
{
178-
m_in.get();
179178
THROW_HR(APPINSTALLER_CLI_ERROR_PROMPT_INPUT_ERROR);
180179
}
181180

src/AppInstallerCLIE2ETests/ConfigureCommand.cs

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ public void OneTimeSetup()
4444
WinGetSettingsHelper.ConfigureFeature("dsc3", true);
4545
this.DeleteResourceArtifacts();
4646
EnsureTestResourcePresence();
47+
TestCommon.SetupTestSource(false);
4748
}
4849

4950
/// <summary>
@@ -54,6 +55,7 @@ public void OneTimeTeardown()
5455
{
5556
WinGetSettingsHelper.ConfigureFeature("dsc3", false);
5657
this.DeleteResourceArtifacts();
58+
TestCommon.TearDownTestSource();
5759
}
5860

5961
/// <summary>
@@ -366,6 +368,39 @@ public void ConfigureFromTestRepo_DSCv3()
366368
Assert.AreEqual("Contents!", File.ReadAllText(targetFilePath));
367369
}
368370

371+
/// <summary>
372+
/// Find unit processors tests.
373+
/// </summary>
374+
[Test]
375+
public void ConfigureFindUnitProcessors()
376+
{
377+
// Find all unit processors.
378+
var result = TestCommon.RunAICLICommand("test config-find-unit-processors", string.Empty);
379+
Assert.AreEqual(0, result.ExitCode);
380+
Assert.True(result.StdOut.Contains("Microsoft/OSInfo"));
381+
382+
// Setup TestExeInstaller with dsc resources.
383+
var installDir = TestCommon.GetRandomTestDir();
384+
result = TestCommon.RunAICLICommand("install", $"AppInstallerTest.TestExeInstaller --override \"/InstallDir {installDir} /GenerateDscResourceFiles\"");
385+
Assert.AreEqual(0, result.ExitCode);
386+
387+
// Find unit processors filtering to install location.
388+
result = TestCommon.RunAICLICommand("test config-find-unit-processors", $"-l {installDir}");
389+
Assert.AreEqual(0, result.ExitCode);
390+
Assert.False(result.StdOut.Contains("Microsoft/OSInfo"));
391+
Assert.True(result.StdOut.Contains("AppInstallerTest/TestResource"));
392+
393+
// Find unit processors filtering to unknown location.
394+
var unknownDir = TestCommon.GetRandomTestDir();
395+
result = TestCommon.RunAICLICommand("test config-find-unit-processors", $"-l {unknownDir}");
396+
Assert.AreEqual(0, result.ExitCode);
397+
Assert.True(result.StdOut.Contains("No unit processors found."));
398+
399+
// Clean up
400+
result = TestCommon.RunAICLICommand("uninstall", "AppInstallerTest.TestExeInstaller");
401+
Assert.AreEqual(0, result.ExitCode);
402+
}
403+
369404
private void DeleteResourceArtifacts()
370405
{
371406
// Delete all .txt files in the test directory; they are placed there by the tests

src/AppInstallerCLIPackage/Package.appxmanifest

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,10 +114,13 @@
114114
<Interface Name="Windows.Foundation.Collections.IIterable`1&lt;Microsoft.Management.Configuration.IApplyGroupMemberSettingsResult&gt;" InterfaceId="5086070C-F468-5B00-8352-50FB420BA8B0" />
115115
<Interface Name="Windows.Foundation.Collections.IIterable`1&lt;Microsoft.Management.Configuration.ITestSettingsResult&gt;" InterfaceId="2D28E6AA-7036-5D78-9B58-9456F1E332FE" />
116116
<Interface Name="Windows.Foundation.Collections.IIterable`1&lt;Microsoft.Management.Configuration.ConfigurationEnvironment&gt;" InterfaceId="47B18106-976B-5532-8E81-F58D304DFA43" />
117+
<Interface Name="Windows.Foundation.Collections.IIterable`1&lt;Microsoft.Management.Configuration.IConfigurationUnitProcessorDetails&gt;" InterfaceId="055865E9-B633-5AD6-9C8F-55DFCD668E74" />
117118
<Interface Name="Microsoft.Management.Configuration.IConfigurationUnitProcessorDetails2" InterfaceId="E89623ED-76E2-5145-B920-D09659554E35" />
118119
<Interface Name="Microsoft.Management.Configuration.IGetAllSettingsConfigurationUnitProcessor" InterfaceId="72EB8304-D8D3-57D4-9940-7C1C4AD8C40C" />
119120
<Interface Name="Microsoft.Management.Configuration.IGetAllUnitsConfigurationUnitProcessor" InterfaceId="D5CB3357-8AD6-5A3C-8695-057C01867D5F" />
121+
<Interface Name="Microsoft.Management.Configuration.IFindUnitProcessorsSetProcessor" InterfaceId="620628DF-A5DE-591A-B738-FD8370B4E95C" />
120122
<Interface Name="Microsoft.Management.Configuration.IConfigurationStatics2" InterfaceId="540BE073-F2EF-5375-83AA-8E23086B0669" />
123+
<Interface Name="Microsoft.Management.Configuration.IConfigurationStatics3" InterfaceId="C84E137B-90E5-5F63-931D-F0497BBCA847" />
121124
<Interface Name="Microsoft.Management.Configuration.SetProcessorFactory.IPwshConfigurationSetProcessorFactoryProperties" InterfaceId="2C298A30-BD3B-5D00-BCD1-2EB633AB7E3B" />
122125
</ProxyStub>
123126
</Extension>

0 commit comments

Comments
 (0)