winget-cli

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README | LICENSE

commit 8503a86490b8d957f422fdb59f55167ac532bd0f
parent 06ac4715513d3807060bd2b08967e0f18934c328
Author: Ryan <69221034+ryfu-msft@users.noreply.github.com>
Date:   Thu, 13 Jun 2024 19:50:45 -0700

Add tests for configure mixed elevation (#4487)


Diffstat:
M.github/actions/spelling/expect.txt | 8++++----
Mazure-pipelines.yml | 1+
Msrc/AppInstallerCLICore/ConfigurationDynamicRuntimeFactory.cpp | 65++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-----
Msrc/AppInstallerCLICore/Workflows/ConfigurationFlow.cpp | 3+--
Msrc/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psd1 | 3++-
Msrc/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psm1 | 38+++++++++++++++++++++++++++++++++++++-
Msrc/Microsoft.Management.Configuration.Processor/Public/PowerShellConfigurationSetProcessorFactory.cs | 2--
Msrc/Microsoft.Management.Configuration.UnitTests/Helpers/Constants.cs | 22+++++++++++++++++++++-
Msrc/Microsoft.Management.Configuration.UnitTests/Helpers/Errors.cs | 3+++
Asrc/Microsoft.Management.Configuration.UnitTests/Helpers/InProcAttribute.cs | 26++++++++++++++++++++++++++
Asrc/Microsoft.Management.Configuration.UnitTests/Helpers/InProcDiscoverer.cs | 40++++++++++++++++++++++++++++++++++++++++
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationDetailsTests.cs | 4+++-
Asrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationMixedElevationTests.cs | 163+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorApplyTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorFactoryTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetAllTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetTests.cs | 4++--
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGroupTests.cs | 1+
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTelemetryTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTestTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetAuthoringTests.cs | 1+
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetProcessorTests.cs | 1+
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitInternalTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitProcessorTests.cs | 2++
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2SimpleFileResourceTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2Tests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/DscResourceMapTests.cs | 4+++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ExceptionExtensionsTests.cs | 4+++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/HashtableExtensionsTests.cs | 9++++++---
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/OpenConfigurationSetTests.cs | 1+
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/PowerShellHelperTests.cs | 4+++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ProcessorEnvironmentTests.cs | 4+++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/SemanticVersionTests.cs | 4+++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/TypeHelpersTests.cs | 3++-
Msrc/Microsoft.Management.Configuration.UnitTests/Tests/ValueSetExtensionsTests.cs | 2++
Msrc/nuget.config | 2+-
36 files changed, 411 insertions(+), 37 deletions(-)

diff --git a/.github/actions/spelling/expect.txt b/.github/actions/spelling/expect.txt @@ -363,7 +363,7 @@ pseudocode PSHOST psobject ptstr -publickey +publickey PVD pvk pvm @@ -413,8 +413,8 @@ servercert servercertificate setmetadatabymanifestid SETTINGCHANGE -SETTINGMAPPING -sfs +SETTINGMAPPING +sfs sfsclient SHCONTF SHGDN @@ -436,7 +436,7 @@ Srinivasan srs startswith STARTUPINFOW -STDMETHODCALLTYPE +STDMETHODCALLTYPE storeapps storeorigin STRRET diff --git a/azure-pipelines.yml b/azure-pipelines.yml @@ -345,6 +345,7 @@ jobs: testSelector: 'testAssemblies' testAssemblyVer2: '**\Microsoft.Management.Configuration.UnitTests.dll' searchFolder: '$(buildOutDir)\Microsoft.Management.Configuration.UnitTests' + testFiltercriteria: 'Category=InProc' codeCoverageEnabled: false platform: '$(buildPlatform)' configuration: '$(BuildConfiguration)' diff --git a/src/AppInstallerCLICore/ConfigurationDynamicRuntimeFactory.cpp b/src/AppInstallerCLICore/ConfigurationDynamicRuntimeFactory.cpp @@ -14,6 +14,28 @@ namespace AppInstaller::CLI::ConfigurationRemoting { namespace anonymous { +#ifndef AICLI_DISABLE_TEST_HOOKS + constexpr std::wstring_view EnableTestModeTestGuid = L"1e62d683-2999-44e7-81f7-6f8f35e8d731"; + constexpr std::wstring_view ForceHighIntegrityLevelUnitsTestGuid = L"f698d20f-3584-4f28-bc75-28037e08e651"; + constexpr std::wstring_view EnableRestrictedIntegrityLevelTestGuid = L"5cae3226-185f-4289-815c-3c089d238dc6"; + + // Checks the configuration set metadata for a specific test guid that controls the behavior flow. + bool GetConfigurationSetMetadataOverride(const ConfigurationSet& configurationSet, const std::wstring_view& testGuid) + { + auto metadataOverride = configurationSet.Metadata().TryLookup(testGuid); + if (metadataOverride) + { + auto metadataOverrideProperty = metadataOverride.try_as<IPropertyValue>(); + if (metadataOverrideProperty && metadataOverrideProperty.Type() == PropertyType::Boolean) + { + return metadataOverrideProperty.GetBoolean(); + } + } + + return false; + } +#endif + struct DynamicProcessorInfo { IConfigurationSetProcessorFactory Factory; @@ -26,7 +48,16 @@ namespace AppInstaller::CLI::ConfigurationRemoting DynamicSetProcessor(IConfigurationSetProcessorFactory defaultRemoteFactory, IConfigurationSetProcessor defaultRemoteSetProcessor, const ConfigurationSet& configurationSet) : m_configurationSet(configurationSet) { +#ifndef AICLI_DISABLE_TEST_HOOKS + m_enableTestMode = GetConfigurationSetMetadataOverride(m_configurationSet, EnableTestModeTestGuid); + m_enableRestrictedIntegrityLevel = GetConfigurationSetMetadataOverride(m_configurationSet, EnableRestrictedIntegrityLevelTestGuid); + m_forceHighIntegrityLevelUnits = GetConfigurationSetMetadataOverride(m_configurationSet, ForceHighIntegrityLevelUnitsTestGuid); + + m_currentIntegrityLevel = m_enableTestMode ? Security::IntegrityLevel::Medium : Security::GetEffectiveIntegrityLevel(); +#else m_currentIntegrityLevel = Security::GetEffectiveIntegrityLevel(); +#endif + m_setProcessors.emplace(m_currentIntegrityLevel, DynamicProcessorInfo{ defaultRemoteFactory, defaultRemoteSetProcessor }); } @@ -56,7 +87,11 @@ namespace AppInstaller::CLI::ConfigurationRemoting }); // Create set and unit processor for current unit. +#ifndef AICLI_DISABLE_TEST_HOOKS + Security::IntegrityLevel requiredIntegrityLevel = m_forceHighIntegrityLevelUnits ? Security::IntegrityLevel::High : GetIntegrityLevelForUnit(unit); +#else Security::IntegrityLevel requiredIntegrityLevel = GetIntegrityLevelForUnit(unit); +#endif auto itr = m_setProcessors.find(requiredIntegrityLevel); if (itr == m_setProcessors.end()) @@ -79,11 +114,20 @@ namespace AppInstaller::CLI::ConfigurationRemoting } else if (securityContextLower == L"restricted") { - // Not supporting elevated callers downgrading at the moment. - THROW_WIN32(ERROR_NOT_SUPPORTED); +#ifndef AICLI_DISABLE_TEST_HOOKS + if (m_enableRestrictedIntegrityLevel) + { + return Security::IntegrityLevel::Medium; + } + else +#endif + { + // Not supporting elevated callers downgrading at the moment. + THROW_WIN32(ERROR_NOT_SUPPORTED); - // Technically this means the default level of the user token, so if UAC is disabled it would be the only integrity level (aka current). - //return Security::IntegrityLevel::Medium; + // Technically this means the default level of the user token, so if UAC is disabled it would be the only integrity level (aka current). + // return Security::IntegrityLevel::Medium; + } } else if (securityContextLower == L"current") { @@ -172,7 +216,12 @@ namespace AppInstaller::CLI::ConfigurationRemoting // If we got here, the only option is that the current integrity level is not High. if (integrityLevel == Security::IntegrityLevel::High) { - factory = CreateOutOfProcessFactory(true, SerializeSetProperties(), SerializeHighIntegrityLevelSet()); + bool useRunAs = true; +#ifndef AICLI_DISABLE_TEST_HOOKS + useRunAs = !m_enableTestMode; +#endif + + factory = CreateOutOfProcessFactory(useRunAs, SerializeSetProperties(), SerializeHighIntegrityLevelSet()); } else { @@ -186,6 +235,12 @@ namespace AppInstaller::CLI::ConfigurationRemoting ProcessorMap m_setProcessors; ConfigurationSet m_configurationSet; std::once_flag m_createUnitSetProcessorsOnce; + +#ifndef AICLI_DISABLE_TEST_HOOKS + bool m_enableTestMode = false; + bool m_enableRestrictedIntegrityLevel = false; + bool m_forceHighIntegrityLevelUnits = false; +#endif }; // This is implemented completely in the packaged context for now, if we want to make it more configurable, we will probably want to move it to configuration and diff --git a/src/AppInstallerCLICore/Workflows/ConfigurationFlow.cpp b/src/AppInstallerCLICore/Workflows/ConfigurationFlow.cpp @@ -100,8 +100,7 @@ namespace AppInstaller::CLI::Workflow IConfigurationSetProcessorFactory factory; // Since downgrading is not currently supported, only use dynamic if not running as admin. - if (Settings::ExperimentalFeature::IsEnabled(Settings::ExperimentalFeature::Feature::ConfigureSelfElevation) && - !Runtime::IsRunningAsAdmin()) + if (Settings::ExperimentalFeature::IsEnabled(Settings::ExperimentalFeature::Feature::ConfigureSelfElevation) && !Runtime::IsRunningAsAdmin()) { factory = ConfigurationRemoting::CreateDynamicRuntimeFactory(); // TODO: Implement SetProcessorFactory::IPwshConfigurationSetProcessorFactoryProperties on dynamic factory diff --git a/src/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psd1 b/src/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psd1 @@ -1,4 +1,4 @@ -# +# # Module manifest for module 'xE2ETestResource' # @@ -22,6 +22,7 @@ DscResourcesToExport = @( 'E2ETestResourceError' 'E2ETestResourceTypes' 'E2ETestResourceCrash' + 'E2ETestResourcePID' ) HelpInfoURI = 'https://www.contoso.com/help' diff --git a/src/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psm1 b/src/AppInstallerCLIE2ETests/TestData/Configuration/Modules/xE2ETestResource/xE2ETestResource.psm1 @@ -1,4 +1,4 @@ -# E2E module with resources. +# E2E module with resources. enum Ensure { @@ -288,3 +288,39 @@ class E2ETestResourceCrash [System.Environment]::Exit(0) } } + +# This resource writes the current PID to the provided file path. +[DscResource()] +class E2ETestResourcePID +{ + [DscProperty(Key)] + [string] $key + + [DscProperty(Mandatory)] + [string] $directoryPath + + [E2ETestResourcePID] Get() + { + $result = @{ + key = "E2ETestResourcePID" + directoryPath = $this.directoryPath + } + + return $result + } + + [bool] Test() + { + return $false + } + + [void] Set() + { + if (Test-Path -Path $this.directoryPath) + { + $processId = [System.Diagnostics.Process]::GetCurrentProcess().Id + $filePath = Join-Path -Path $this.directoryPath -ChildPath "$processId.txt" + New-Item -Path $filePath -ItemType File -Force + } + } +} diff --git a/src/Microsoft.Management.Configuration.Processor/Public/PowerShellConfigurationSetProcessorFactory.cs b/src/Microsoft.Management.Configuration.Processor/Public/PowerShellConfigurationSetProcessorFactory.cs @@ -8,9 +8,7 @@ namespace Microsoft.Management.Configuration.Processor { using System; using System.Collections.Generic; - using System.ComponentModel; using System.IO; - using System.Linq; using System.Management.Automation; using System.Runtime.CompilerServices; using System.Text; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Helpers/Constants.cs b/src/Microsoft.Management.Configuration.UnitTests/Helpers/Constants.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="Constants.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -20,5 +20,25 @@ namespace Microsoft.Management.Configuration.UnitTests.Helpers /// The namespace where xUnit traits will be defined. /// </summary> public const string NamespaceNameForTraits = "Microsoft.Management.Configuration.UnitTests.Helpers"; + + /// <summary> + /// The dynamic runtime factory handler identifier. + /// </summary> + public const string DynamicRuntimeHandlerIdentifier = "{73fea39f-6f4a-41c9-ba94-6fd14d633e40}"; + + /// <summary> + /// Test guid for enabling test mode for the dynamic runtime factory. Forces factory to exclude 'runas' verb and sets current IL to medium. + /// </summary> + public const string EnableDynamicFactoryTestMode = "1e62d683-2999-44e7-81f7-6f8f35e8d731"; + + /// <summary> + /// Test guid for allowing the restricted integrity level to be supported. + /// </summary> + public const string EnableRestrictedIntegrityLevelTestGuid = "5cae3226-185f-4289-815c-3c089d238dc6"; + + /// <summary> + /// Test guid for forcing units to have a high integrity level during the final routing of unit processor creation. + /// </summary> + public const string ForceHighIntegrityLevelUnitsTestGuid = "f698d20f-3584-4f28-bc75-28037e08e651"; } } diff --git a/src/Microsoft.Management.Configuration.UnitTests/Helpers/Errors.cs b/src/Microsoft.Management.Configuration.UnitTests/Helpers/Errors.cs @@ -47,6 +47,9 @@ namespace Microsoft.Management.Configuration.UnitTests.Helpers public static readonly int WINGET_CONFIG_ERROR_UNIT_IMPORT_MODULE_ADMIN = unchecked((int)0x8A15C111); public static readonly int WINGET_CONFIG_ERROR_NOT_SUPPORTED_BY_PROCESSOR = unchecked((int)0x8A15C112); + // Limitation Set Errors + public static readonly int CORE_INVALID_OPERATION = unchecked((int)0x80131509); + #pragma warning restore SA1025 // Code should not contain multiple whitespace in a row #pragma warning restore SA1600 // Elements should be documented #pragma warning restore SA1310 // Field names should not contain underscore diff --git a/src/Microsoft.Management.Configuration.UnitTests/Helpers/InProcAttribute.cs b/src/Microsoft.Management.Configuration.UnitTests/Helpers/InProcAttribute.cs @@ -0,0 +1,26 @@ +// ----------------------------------------------------------------------------- +// <copyright file="InProcAttribute.cs" company="Microsoft Corporation"> +// Copyright (c) Microsoft Corporation. Licensed under the MIT License. +// </copyright> +// ----------------------------------------------------------------------------- + +namespace Microsoft.Management.Configuration.UnitTests.Helpers +{ + using System; + using Xunit.Sdk; + + /// <summary> + /// Trait used to mark a test as only for the in proc scenario. + /// </summary> + [TraitDiscoverer(InProcDiscoverer.TypeName, Constants.AssemblyNameForTraits)] + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false)] + public class InProcAttribute : Attribute, ITraitAttribute + { + /// <summary> + /// Initializes a new instance of the <see cref="InProcAttribute"/> class. + /// </summary> + public InProcAttribute() + { + } + } +} diff --git a/src/Microsoft.Management.Configuration.UnitTests/Helpers/InProcDiscoverer.cs b/src/Microsoft.Management.Configuration.UnitTests/Helpers/InProcDiscoverer.cs @@ -0,0 +1,40 @@ +// ----------------------------------------------------------------------------- +// <copyright file="InProcDiscoverer.cs" company="Microsoft Corporation"> +// Copyright (c) Microsoft Corporation. Licensed under the MIT License. +// </copyright> +// ----------------------------------------------------------------------------- + +namespace Microsoft.Management.Configuration.UnitTests.Helpers +{ + using System.Collections.Generic; + using Xunit.Abstractions; + using Xunit.Sdk; + + /// <summary> + /// Enables integration with xUnit trait system. + /// </summary> + public class InProcDiscoverer : ITraitDiscoverer + { + /// <summary> + /// The type name for this discoverer. + /// </summary> + public const string TypeName = Constants.NamespaceNameForTraits + ".InProcDiscoverer"; + + /// <summary> + /// Initializes a new instance of the <see cref="InProcDiscoverer"/> class. + /// </summary> + public InProcDiscoverer() + { + } + + /// <summary> + /// Gets the trait information for the InProcAttribute. + /// </summary> + /// <param name="traitAttribute">The trait information.</param> + /// <returns>Trait name/value pairs.</returns> + public IEnumerable<KeyValuePair<string, string>> GetTraits(IAttributeInfo traitAttribute) + { + yield return new KeyValuePair<string, string>("Category", "InProc"); + } + } +} diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationDetailsTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationDetailsTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationDetailsTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -14,6 +14,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using Microsoft.Management.Configuration.Processor.Helpers; using Microsoft.Management.Configuration.Processor.Unit; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Windows.Security.Cryptography.Certificates; using Xunit; using Xunit.Abstractions; @@ -22,6 +23,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Tests for ConfigurationUnitProcessorDetails and ConfigurationUnitSettingDetails. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationDetailsTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationMixedElevationTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationMixedElevationTests.cs @@ -0,0 +1,163 @@ +// ----------------------------------------------------------------------------- +// <copyright file="ConfigurationMixedElevationTests.cs" company="Microsoft Corporation"> +// Copyright (c) Microsoft Corporation. Licensed under the MIT License. +// </copyright> +// ----------------------------------------------------------------------------- + +namespace Microsoft.Management.Configuration.UnitTests.Tests +{ + using System; + using System.IO; + using System.Threading.Tasks; + using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; + using Xunit; + using Xunit.Abstractions; + + /// <summary> + /// Unit tests for verifying the processor behavior for handling mixed elevation scenarios. + /// </summary> + [Collection("UnitTestCollection")] + [OutOfProc] + public class ConfigurationMixedElevationTests : ConfigurationProcessorTestBase + { + private readonly UnitTestFixture fixture; + private readonly ITestOutputHelper log; + + /// <summary> + /// Initializes a new instance of the <see cref="ConfigurationMixedElevationTests"/> class. + /// </summary> + /// <param name="fixture">Unit test fixture.</param> + /// <param name="log">Log helper.</param> + public ConfigurationMixedElevationTests(UnitTestFixture fixture, ITestOutputHelper log) + : base(fixture, log) + { + this.fixture = fixture; + this.log = log; + } + + /// <summary> + /// Verifies that applying units of mixed elevation is successful. Also verifies that the elevated processor has a different process id. + /// </summary> + /// <returns>A <see cref="Task"/> representing the asynchronous unit test.</returns> + [Fact] + public async Task ApplyMixedElevationUnits() + { + string resourceName = "E2ETestResourcePID"; + string moduleName = "xE2ETestResource"; + Version version = new Version("0.0.0.1"); + + string tempDirectory = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName()); + Directory.CreateDirectory(tempDirectory); + + ConfigurationSet configurationSet = this.ConfigurationSet(); + configurationSet.Metadata.Add(Helpers.Constants.EnableDynamicFactoryTestMode, true); + + ConfigurationUnit unit = this.ConfigurationUnit(); + unit.Metadata.Add("version", version.ToString()); + unit.Metadata.Add("module", moduleName); + unit.Settings.Add("directoryPath", tempDirectory); + unit.Type = resourceName; + unit.Intent = ConfigurationUnitIntent.Apply; + + ConfigurationUnit elevatedUnit = this.ConfigurationUnit(); + elevatedUnit.Metadata.Add("version", version.ToString()); + elevatedUnit.Metadata.Add("module", moduleName); + elevatedUnit.Metadata.Add("securityContext", "elevated"); + elevatedUnit.Settings.Add("directoryPath", tempDirectory); + elevatedUnit.Type = resourceName; + elevatedUnit.Intent = ConfigurationUnitIntent.Apply; + + configurationSet.Units = new ConfigurationUnit[] { unit, elevatedUnit }; + + IConfigurationSetProcessorFactory dynamicFactory = await this.fixture.ConfigurationStatics.CreateConfigurationSetProcessorFactoryAsync(Helpers.Constants.DynamicRuntimeHandlerIdentifier); + + ConfigurationProcessor processor = this.CreateConfigurationProcessorWithDiagnostics(dynamicFactory); + + ApplyConfigurationSetResult result = processor.ApplySet(configurationSet, ApplyConfigurationSetFlags.None); + + // Get the number of unique PIDs from temp directory. + int pidCount = Directory.GetFiles(tempDirectory).Length; + + // Clean up temp directory folder. + Directory.Delete(tempDirectory, true); + + Assert.NotNull(result); + Assert.Null(result.ResultCode); + Assert.Equal(2, result.UnitResults.Count); + + foreach (var unitResult in result.UnitResults) + { + Assert.NotNull(unitResult); + Assert.False(unitResult.PreviouslyInDesiredState); + Assert.False(unitResult.RebootRequired); + Assert.NotNull(unitResult.ResultInformation); + Assert.Null(unitResult.ResultInformation.ResultCode); + Assert.Equal(ConfigurationUnitResultSource.None, unitResult.ResultInformation.ResultSource); + } + + // There should be exactly 2 unique PIDs, one for each integrity level. + Assert.Equal(2, pidCount); + } + + /// <summary> + /// Verifies that creating a high integrity unit processor for a non elevated unit should return an invalid operation result. + /// </summary> + /// <returns>A <see cref="Task"/> representing the asynchronous unit test.</returns> + [Fact] + public async Task ApplyUnitNotInLimitationSet() + { + string resourceName = "E2ETestResource"; + string moduleName = "xE2ETestResource"; + Version version = new Version("0.0.0.1"); + + ConfigurationSet configurationSet = this.ConfigurationSet(); + configurationSet.Metadata.Add(Helpers.Constants.EnableDynamicFactoryTestMode, true); + configurationSet.Metadata.Add(Helpers.Constants.ForceHighIntegrityLevelUnitsTestGuid, true); + configurationSet.Metadata.Add(Helpers.Constants.EnableRestrictedIntegrityLevelTestGuid, true); + + ConfigurationUnit unit = this.ConfigurationUnit(); + unit.Metadata.Add("version", version.ToString()); + unit.Metadata.Add("module", moduleName); + unit.Type = resourceName; + unit.Intent = ConfigurationUnitIntent.Apply; + + ConfigurationUnit elevatedUnit = this.ConfigurationUnit(); + elevatedUnit.Metadata.Add("version", version.ToString()); + elevatedUnit.Metadata.Add("module", moduleName); + elevatedUnit.Metadata.Add("securityContext", "elevated"); + elevatedUnit.Type = resourceName; + elevatedUnit.Intent = ConfigurationUnitIntent.Apply; + + configurationSet.Units = new ConfigurationUnit[] { unit, elevatedUnit }; + + IConfigurationSetProcessorFactory dynamicFactory = await this.fixture.ConfigurationStatics.CreateConfigurationSetProcessorFactoryAsync(Helpers.Constants.DynamicRuntimeHandlerIdentifier); + + ConfigurationProcessor processor = this.CreateConfigurationProcessorWithDiagnostics(dynamicFactory); + + ApplyConfigurationSetResult result = processor.ApplySet(configurationSet, ApplyConfigurationSetFlags.None); + Assert.NotNull(result); + Assert.NotNull(result.ResultCode); + Assert.Equal(Errors.WINGET_CONFIG_ERROR_SET_APPLY_FAILED, result.ResultCode.HResult); + Assert.Equal(2, result.UnitResults.Count); + + ApplyConfigurationUnitResult unitResult = result.UnitResults[0]; + Assert.NotNull(unitResult); + Assert.False(unitResult.PreviouslyInDesiredState); + Assert.False(unitResult.RebootRequired); + Assert.NotNull(unitResult.ResultInformation); + Assert.NotNull(unitResult.ResultInformation.ResultCode); + Assert.Equal(Errors.CORE_INVALID_OPERATION, unitResult.ResultInformation.ResultCode.HResult); + Assert.Equal(ConfigurationUnitResultSource.Internal, unitResult.ResultInformation.ResultSource); + + // Elevated unit should still succeed when applied. + ApplyConfigurationUnitResult elevatedUnitResult = result.UnitResults[1]; + Assert.NotNull(elevatedUnitResult); + Assert.False(elevatedUnitResult.PreviouslyInDesiredState); + Assert.False(elevatedUnitResult.RebootRequired); + Assert.NotNull(elevatedUnitResult.ResultInformation); + Assert.Null(elevatedUnitResult.ResultInformation.ResultCode); + Assert.Equal(ConfigurationUnitResultSource.None, elevatedUnitResult.ResultInformation.ResultSource); + } + } +} diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorApplyTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorApplyTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationProcessorApplyTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -21,6 +21,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for running apply on the processor. /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class ConfigurationProcessorApplyTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorFactoryTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorFactoryTests.cs @@ -10,7 +10,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using Microsoft.Management.Configuration.Processor; using Microsoft.Management.Configuration.Processor.Set; using Microsoft.Management.Configuration.UnitTests.Fixtures; - using Moq; + using Microsoft.Management.Configuration.UnitTests.Helpers; using WinRT; using Xunit; using Xunit.Abstractions; @@ -20,6 +20,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Tests ConfigurationProcessorFactory. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationProcessorFactoryTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetAllTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetAllTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationProcessorGetAllTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -19,6 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for getting details on processors. /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class ConfigurationProcessorGetAllTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGetTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationProcessorGetTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -6,7 +6,6 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests { - using System.Collections.Generic; using System.IO; using Microsoft.Management.Configuration.UnitTests.Fixtures; using Microsoft.Management.Configuration.UnitTests.Helpers; @@ -18,6 +17,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for getting details on processors. /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class ConfigurationProcessorGetTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGroupTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorGroupTests.cs @@ -19,6 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for running group processing. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationProcessorGroupTests : ConfigurationProcessorTestBase { /// <summary> diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTelemetryTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTelemetryTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationProcessorTelemetryTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -25,6 +25,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for running test on the processor. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationProcessorTelemetryTests : ConfigurationProcessorTestBase { /// <summary> diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTestTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationProcessorTestTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationProcessorTestTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -19,6 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for running test on the processor. /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class ConfigurationProcessorTestTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetAuthoringTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetAuthoringTests.cs @@ -19,6 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for configuration set authoring (creating objects). /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class ConfigurationSetAuthoringTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetProcessorTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationSetProcessorTests.cs @@ -28,6 +28,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for configuration processor tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationSetProcessorTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitInternalTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitInternalTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ConfigurationUnitInternalTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -22,6 +22,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Tests ConfigurationUnitExtensionsTests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationUnitInternalTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitProcessorTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ConfigurationUnitProcessorTests.cs @@ -16,6 +16,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using Microsoft.Management.Configuration.Processor.ProcessorEnvironments; using Microsoft.Management.Configuration.Processor.Unit; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Microsoft.PowerShell.Commands; using Moq; using Windows.Foundation.Collections; @@ -26,6 +27,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Configuration unit processor tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ConfigurationUnitProcessorTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2SimpleFileResourceTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2SimpleFileResourceTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="DscModuleV2SimpleFileResourceTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -21,6 +21,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Class that tests a little not that complex resource. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class DscModuleV2SimpleFileResourceTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2Tests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/DscModuleV2Tests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="DscModuleV2Tests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -24,6 +24,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Tests DscModuleV2 with really simple resources. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class DscModuleV2Tests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/DscResourceMapTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/DscResourceMapTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="DscResourceMapTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -11,6 +11,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using Microsoft.Management.Configuration.Processor.DscResourcesInfo; using Microsoft.Management.Configuration.Processor.Helpers; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Xunit; using Xunit.Abstractions; @@ -18,6 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// DscResourceMap tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class DscResourceMapTests { private const string ResourceZoro = "xResourceZoro"; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ExceptionExtensionsTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ExceptionExtensionsTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ExceptionExtensionsTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -9,6 +9,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System; using Microsoft.Management.Configuration.Processor.Extensions; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Microsoft.PowerShell.Commands; using Xunit; using Xunit.Abstractions; @@ -17,6 +18,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Exception extension tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ExceptionExtensionsTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/HashtableExtensionsTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/HashtableExtensionsTests.cs @@ -9,7 +9,8 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System.Collections; using Microsoft.Management.Configuration.Processor.Exceptions; using Microsoft.Management.Configuration.Processor.Extensions; - using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Windows.Foundation.Collections; using Xunit; using Xunit.Abstractions; @@ -17,7 +18,8 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// <summary> /// Hashtable extension tests. /// </summary> - [Collection("UnitTestCollection")] + [Collection("UnitTestCollection")] + [InProc] public class HashtableExtensionsTests { private readonly UnitTestFixture fixture; @@ -67,7 +69,8 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests { var ht = new Hashtable() { - { "hashtableKey", new Hashtable() + { + "hashtableKey", new Hashtable() { { "key1", "value1" }, { "key2", 2 }, diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/OpenConfigurationSetTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/OpenConfigurationSetTests.cs @@ -25,6 +25,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Unit tests for parsing configuration sets from streams. /// </summary> [Collection("UnitTestCollection")] + [InProc] [OutOfProc] public class OpenConfigurationSetTests : ConfigurationProcessorTestBase { diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/PowerShellHelperTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/PowerShellHelperTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="PowerShellHelperTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -9,6 +9,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System; using Microsoft.Management.Configuration.Processor.Helpers; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Xunit; using Xunit.Abstractions; @@ -16,6 +17,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// PowerShell helper tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class PowerShellHelperTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ProcessorEnvironmentTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ProcessorEnvironmentTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="ProcessorEnvironmentTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -8,6 +8,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests { using System.Collections.Generic; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Moq; using Xunit; using Xunit.Abstractions; @@ -17,6 +18,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// HostedEnvironment tests, that is more ProcessorEnvironmentBase tests for non forwarding functions. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ProcessorEnvironmentTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/SemanticVersionTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/SemanticVersionTests.cs @@ -1,4 +1,4 @@ -// ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- // <copyright file="SemanticVersionTests.cs" company="Microsoft Corporation"> // Copyright (c) Microsoft Corporation. Licensed under the MIT License. // </copyright> @@ -9,6 +9,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System; using Microsoft.Management.Configuration.Processor.Helpers; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Xunit; using Xunit.Abstractions; @@ -16,6 +17,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// Semantic version tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class SemanticVersionTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/TypeHelpersTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/TypeHelpersTests.cs @@ -10,6 +10,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System.Collections.Generic; using Microsoft.Management.Configuration.Processor.Helpers; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Windows.Foundation.Collections; using Xunit; using Xunit.Abstractions; @@ -18,7 +19,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// TypeHelpers tests. /// </summary> [Collection("UnitTestCollection")] - + [InProc] public class TypeHelpersTests { private readonly UnitTestFixture fixture; diff --git a/src/Microsoft.Management.Configuration.UnitTests/Tests/ValueSetExtensionsTests.cs b/src/Microsoft.Management.Configuration.UnitTests/Tests/ValueSetExtensionsTests.cs @@ -11,6 +11,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests using System.Collections.Generic; using Microsoft.Management.Configuration.Processor.Extensions; using Microsoft.Management.Configuration.UnitTests.Fixtures; + using Microsoft.Management.Configuration.UnitTests.Helpers; using Windows.Foundation.Collections; using Xunit; using Xunit.Abstractions; @@ -19,6 +20,7 @@ namespace Microsoft.Management.Configuration.UnitTests.Tests /// ValueSet extension tests. /// </summary> [Collection("UnitTestCollection")] + [InProc] public class ValueSetExtensionsTests { private readonly UnitTestFixture fixture; diff --git a/src/nuget.config b/src/nuget.config @@ -1,4 +1,4 @@ -<?xml version="1.0" encoding="utf-8"?> +<?xml version="1.0" encoding="utf-8"?> <configuration> <packageSources> <clear />