diff --git a/.ci/test.yml b/.ci/test.yml index cd8c8c88f..e59b14ad1 100644 --- a/.ci/test.yml +++ b/.ci/test.yml @@ -107,10 +107,12 @@ jobs: inputs: azureSubscription: PSResourceGetACR azurePowerShellVersion: LatestVersion + pwsh: true ScriptType: InlineScript inline: | $modulePath = Join-Path -Path $env:AGENT_TEMPDIRECTORY -ChildPath 'TempModules' $env:PSModulePath = $modulePath + [System.IO.Path]::PathSeparator + $env:PSModulePath + Write-Verbose -Verbose "Importing build utilities (buildtools.psd1)" Import-Module -Name (Join-Path -Path '${{ parameters.buildDirectory }}' -ChildPath 'buildtools.psd1') -Force Invoke-ModuleTestsACR -Type Functional diff --git a/global.json b/global.json index 77d62424a..fb6d6a3df 100644 --- a/global.json +++ b/global.json @@ -1,5 +1,5 @@ { "sdk": { - "version": "8.0.406" + "version": "8.0.411" } } diff --git a/src/code/ContainerRegistryServerAPICalls.cs b/src/code/ContainerRegistryServerAPICalls.cs index 785c7aeae..5dab4c49e 100644 --- a/src/code/ContainerRegistryServerAPICalls.cs +++ b/src/code/ContainerRegistryServerAPICalls.cs @@ -394,6 +394,8 @@ internal string GetContainerRegistryAccessToken(out ErrorRecord errRecord) else { bool isRepositoryUnauthenticated = IsContainerRegistryUnauthenticated(Repository.Uri.ToString(), out errRecord, out accessToken); + _cmdletPassedIn.WriteDebug($"Is repository unauthenticated: {isRepositoryUnauthenticated}"); + if (errRecord != null) { return null; @@ -407,7 +409,7 @@ internal string GetContainerRegistryAccessToken(out ErrorRecord errRecord) if (!isRepositoryUnauthenticated) { - accessToken = Utils.GetAzAccessToken(); + accessToken = Utils.GetAzAccessToken(_cmdletPassedIn); if (string.IsNullOrEmpty(accessToken)) { errRecord = new ErrorRecord( @@ -488,6 +490,8 @@ internal bool IsContainerRegistryUnauthenticated(string containerRegistyUrl, out // get the anonymous access token var url = $"{realm}?service={service}{defaultScope}"; + _cmdletPassedIn.WriteDebug($"Getting anonymous access token from the realm: {url}"); + // we dont check the errorrecord here because we want to return false if we get a 401 and not throw an error var results = GetHttpResponseJObjectUsingContentHeaders(url, HttpMethod.Get, content, contentHeaders, out _); diff --git a/src/code/FindPSResource.cs b/src/code/FindPSResource.cs index d2a78b1a6..2709073e7 100644 --- a/src/code/FindPSResource.cs +++ b/src/code/FindPSResource.cs @@ -24,7 +24,7 @@ namespace Microsoft.PowerShell.PSResourceGet.Cmdlets public sealed class FindPSResource : PSCmdlet { #region Members - + private const string NameParameterSet = "NameParameterSet"; private const string CommandNameParameterSet = "CommandNameParameterSet"; private const string DscResourceNameParameterSet = "DscResourceNameParameterSet"; @@ -39,7 +39,7 @@ public sealed class FindPSResource : PSCmdlet /// Specifies name of a resource or resources to find. Accepts wild card characters. /// [SupportsWildcards] - [Parameter(Position = 0, + [Parameter(Position = 0, ValueFromPipeline = true, ValueFromPipelineByPropertyName = true, ParameterSetName = NameParameterSet)] @@ -167,7 +167,6 @@ protected override void ProcessRecord() private void ProcessResourceNameParameterSet() { - WriteDebug("In FindPSResource::ProcessResourceNameParameterSet()"); // only cases where Name is allowed to not be specified is if Type or Tag parameters are if (!MyInvocation.BoundParameters.ContainsKey(nameof(Name))) { @@ -178,7 +177,7 @@ private void ProcessResourceNameParameterSet() } else if (MyInvocation.BoundParameters.ContainsKey(nameof(Type))) { - Name = new string[] {"*"}; + Name = new string[] { "*" }; } else { @@ -191,8 +190,8 @@ private void ProcessResourceNameParameterSet() } WriteDebug("Filtering package name(s) on wildcards"); - Name = Utils.ProcessNameWildcards(Name, removeWildcardEntries:false, out string[] errorMsgs, out bool nameContainsWildcard); - + Name = Utils.ProcessNameWildcards(Name, removeWildcardEntries: false, out string[] errorMsgs, out bool nameContainsWildcard); + foreach (string error in errorMsgs) { WriteError(new ErrorRecord( @@ -208,7 +207,7 @@ private void ProcessResourceNameParameterSet() { WriteDebug("Package name(s) could not be resolved"); return; - } + } // determine/parse out Version param VersionType versionType = VersionType.VersionRange; @@ -232,7 +231,7 @@ private void ProcessResourceNameParameterSet() "IncorrectVersionFormat", ErrorCategory.InvalidArgument, this)); - + return; } } @@ -289,7 +288,7 @@ private void ProcessCommandOrDscParameterSet(bool isSearchingForCommands) WriteDebug("Command or DSCResource name(s) could not be resolved"); return; } - + foreach (PSCommandResourceInfo cmdPkg in _findHelper.FindByCommandOrDscResource( isSearchingForCommands: isSearchingForCommands, prerelease: Prerelease, @@ -325,7 +324,7 @@ private void ProcessTags() WriteDebug("Tags(s) could not be resolved"); return; } - + foreach (PSResourceInfo tagPkg in _findHelper.FindByTag( type: Type, prerelease: Prerelease, diff --git a/src/code/Microsoft.PowerShell.PSResourceGet.csproj b/src/code/Microsoft.PowerShell.PSResourceGet.csproj index 1d657e1a1..225c4292e 100644 --- a/src/code/Microsoft.PowerShell.PSResourceGet.csproj +++ b/src/code/Microsoft.PowerShell.PSResourceGet.csproj @@ -24,7 +24,7 @@ - + diff --git a/src/code/RegisterPSResourceRepository.cs b/src/code/RegisterPSResourceRepository.cs index 1a86db210..97e18bdc9 100644 --- a/src/code/RegisterPSResourceRepository.cs +++ b/src/code/RegisterPSResourceRepository.cs @@ -102,7 +102,7 @@ class RegisterPSResourceRepository : PSCmdlet /// [Parameter] public SwitchParameter PassThru { get; set; } - + /// /// When specified, will overwrite information for any existing repository with the same name. /// @@ -212,14 +212,14 @@ private PSRepositoryInfo PSGalleryParameterSetHelper(int repoPriority, bool repo WriteDebug("In RegisterPSResourceRepository::PSGalleryParameterSetHelper()"); Uri psGalleryUri = new Uri(PSGalleryRepoUri); WriteDebug("Internal name and uri values for PSGallery are hardcoded and validated. Priority and trusted values, if passed in, also validated"); - var addedRepo = RepositorySettings.AddToRepositoryStore(PSGalleryRepoName, - psGalleryUri, - repoPriority, - repoTrusted, + var addedRepo = RepositorySettings.AddToRepositoryStore(PSGalleryRepoName, + psGalleryUri, + repoPriority, + repoTrusted, apiVersion: null, - repoCredentialInfo: null, - Force, - this, + repoCredentialInfo: null, + Force, + this, out string errorMsg); if (!string.IsNullOrEmpty(errorMsg)) @@ -313,7 +313,7 @@ private PSRepositoryInfo RepoValidationHelper(Hashtable repo) "NullUriForRepositoriesParameterSetRegistration", ErrorCategory.InvalidArgument, this)); - + return null; } @@ -337,10 +337,10 @@ private PSRepositoryInfo RepoValidationHelper(Hashtable repo) return null; } - if (repo.ContainsKey("ApiVersion") && + if (repo.ContainsKey("ApiVersion") && (repo["ApiVersion"] == null || String.IsNullOrEmpty(repo["ApiVersion"].ToString()) || - !(repo["ApiVersion"].ToString().Equals("Local", StringComparison.OrdinalIgnoreCase) || repo["ApiVersion"].ToString().Equals("V2", StringComparison.OrdinalIgnoreCase) || - repo["ApiVersion"].ToString().Equals("V3", StringComparison.OrdinalIgnoreCase) || repo["ApiVersion"].ToString().Equals("NugetServer", StringComparison.OrdinalIgnoreCase) || + !(repo["ApiVersion"].ToString().Equals("Local", StringComparison.OrdinalIgnoreCase) || repo["ApiVersion"].ToString().Equals("V2", StringComparison.OrdinalIgnoreCase) || + repo["ApiVersion"].ToString().Equals("V3", StringComparison.OrdinalIgnoreCase) || repo["ApiVersion"].ToString().Equals("NugetServer", StringComparison.OrdinalIgnoreCase) || repo["ApiVersion"].ToString().Equals("Unknown", StringComparison.OrdinalIgnoreCase)))) { WriteError(new ErrorRecord( diff --git a/src/code/Utils.cs b/src/code/Utils.cs index 89de7cd10..5ca14d0e2 100644 --- a/src/code/Utils.cs +++ b/src/code/Utils.cs @@ -648,12 +648,11 @@ public static PSCredential GetRepositoryCredentialFromSecretManagement( } } - public static string GetAzAccessToken() + public static string GetAzAccessToken(PSCmdlet cmdletPassedIn) { var credOptions = new DefaultAzureCredentialOptions { ExcludeEnvironmentCredential = true, - ExcludeVisualStudioCodeCredential = true, ExcludeVisualStudioCredential = true, ExcludeWorkloadIdentityCredential = true, ExcludeManagedIdentityCredential = true, // ManagedIdentityCredential makes the experience slow @@ -665,8 +664,25 @@ public static string GetAzAccessToken() var dCred = new DefaultAzureCredential(credOptions); var tokenRequestContext = new TokenRequestContext(new string[] { "https://management.azure.com/.default" }); - var token = dCred.GetTokenAsync(tokenRequestContext).Result; - return token.Token; + + try + { + using (var cts = new CancellationTokenSource(TimeSpan.FromSeconds(30))) + { + var token = dCred.GetTokenAsync(tokenRequestContext, cts.Token).GetAwaiter().GetResult(); + return token.Token; + } + } + catch (OperationCanceledException) + { + cmdletPassedIn.WriteWarning("Timeout occurred while acquiring Azure access token."); + return null; + } + catch (Exception ex) + { + cmdletPassedIn.WriteWarning($"Failed to acquire Azure access token: {ex.Message}"); + return null; + } } public static string GetContainerRegistryAccessTokenFromSecretManagement( @@ -1874,9 +1890,9 @@ public static Hashtable GetMetadataFromNuspec(string nuspecFilePath, PSCmdlet cm catch (Exception e) { errorRecord = new ErrorRecord( - exception: e, - "GetHashtableForNuspecFailure", - ErrorCategory.ReadError, + exception: e, + "GetHashtableForNuspecFailure", + ErrorCategory.ReadError, cmdletPassedIn); } @@ -1895,9 +1911,9 @@ public static XmlDocument LoadXmlDocument(string filePath, PSCmdlet cmdletPassed catch (Exception e) { errRecord = new ErrorRecord( - exception: e, - "LoadXmlDocumentFailure", - ErrorCategory.ReadError, + exception: e, + "LoadXmlDocumentFailure", + ErrorCategory.ReadError, cmdletPassedIn); }