diff --git a/src/Bicep.Cli/Arguments/PublishProviderArguments.cs b/src/Bicep.Cli/Arguments/PublishProviderArguments.cs index 45df757c977..fb1a3039cb3 100644 --- a/src/Bicep.Cli/Arguments/PublishProviderArguments.cs +++ b/src/Bicep.Cli/Arguments/PublishProviderArguments.cs @@ -28,7 +28,7 @@ public PublishProviderArguments(string[] args) : base(Constants.Command.PublishP i++; break; - case {} when args[i].StartsWith("--bin-"): + case { } when args[i].StartsWith("--bin-"): var architectureName = args[i].Substring("--bin-".Length); if (!SupportedArchitectures.All.Any(x => x.Name == architectureName)) diff --git a/src/Bicep.Cli/Commands/LocalDeployCommand.cs b/src/Bicep.Cli/Commands/LocalDeployCommand.cs index e065580bc5c..b43ad5acf5f 100644 --- a/src/Bicep.Cli/Commands/LocalDeployCommand.cs +++ b/src/Bicep.Cli/Commands/LocalDeployCommand.cs @@ -1,8 +1,6 @@ // Copyright (c) Microsoft Corporation. // Licensed under the MIT License. -using Bicep.Local.Deploy; -using Bicep.Local.Deploy.Extensibility; using Azure.Deployments.Core.Json; using Bicep.Cli.Arguments; using Bicep.Cli.Helpers; @@ -12,6 +10,8 @@ using Bicep.Core.Registry; using Bicep.Core.Semantics; using Bicep.Core.TypeSystem.Types; +using Bicep.Local.Deploy; +using Bicep.Local.Deploy.Extensibility; using Bicep.Local.Extension.Rpc; using Microsoft.Extensions.Logging; using Newtonsoft.Json; @@ -53,8 +53,8 @@ public async Task<int> RunAsync(LocalDeployArguments args, CancellationToken can var parameters = compilation.Emitter.Parameters(); if (summary.HasErrors || - parameters.Parameters is not {} parametersString || - parameters.Template?.Template is not {} templateString) + parameters.Parameters is not { } parametersString || + parameters.Template?.Template is not { } templateString) { return 1; } @@ -76,7 +76,7 @@ parameters.Parameters is not {} parametersString || private async Task WriteSummary(LocalDeployment.Result result) { - if (result.Deployment.Properties.Outputs is {} outputs) + if (result.Deployment.Properties.Outputs is { } outputs) { foreach (var output in outputs) { @@ -84,7 +84,7 @@ private async Task WriteSummary(LocalDeployment.Result result) } } - if (result.Deployment.Properties.Error is {} error) + if (result.Deployment.Properties.Error is { } error) { foreach (var subError in error.Details) { @@ -99,4 +99,4 @@ private async Task WriteSummary(LocalDeployment.Result result) await io.Output.WriteLineAsync($"Result: {result.Deployment.Properties.ProvisioningState}"); } -} \ No newline at end of file +} diff --git a/src/Bicep.Cli/Commands/PublishProviderCommand.cs b/src/Bicep.Cli/Commands/PublishProviderCommand.cs index a5ac9f8a352..d9c06761eb8 100644 --- a/src/Bicep.Cli/Commands/PublishProviderCommand.cs +++ b/src/Bicep.Cli/Commands/PublishProviderCommand.cs @@ -44,7 +44,7 @@ public async Task<int> RunAsync(PublishProviderArguments args) { ProviderBinary? TryGetBinary(SupportedArchitecture architecture) { - if (args.Binaries.TryGetValue(architecture.Name) is not {} binaryPath) + if (args.Binaries.TryGetValue(architecture.Name) is not { } binaryPath) { return null; } diff --git a/src/Bicep.Core/Emit/TemplateWriter.cs b/src/Bicep.Core/Emit/TemplateWriter.cs index e26a06735e3..7c93bb23a9f 100644 --- a/src/Bicep.Core/Emit/TemplateWriter.cs +++ b/src/Bicep.Core/Emit/TemplateWriter.cs @@ -1223,10 +1223,10 @@ private void EmitModuleParameters(ExpressionEmitter emitter, DeclaredModuleExpre private void EmitModuleForLocalDeploy(PositionTrackingJsonTextWriter jsonWriter, DeclaredModuleExpression module, ExpressionEmitter emitter) { - emitter.EmitObject(() => + emitter.EmitObject(() => { emitter.EmitProperty("import", "az0synthesized"); - + var body = module.Body; if (body is ForLoopExpression forLoop) { diff --git a/src/Bicep.Core/Registry/AzureContainerRegistryManager.cs b/src/Bicep.Core/Registry/AzureContainerRegistryManager.cs index 12d2c2001cc..d24a2a3f94b 100644 --- a/src/Bicep.Core/Registry/AzureContainerRegistryManager.cs +++ b/src/Bicep.Core/Registry/AzureContainerRegistryManager.cs @@ -155,7 +155,7 @@ private static async Task<OciArtifactResult> DownloadManifestAndLayersAsync(IOci .Select(async layer => new OciArtifactLayer(layer.Digest, layer.MediaType, await PullLayerAsync(client, layer))); var layers = await Task.WhenAll(layerTasks); - var config = !deserializedManifest.Config.IsEmpty() ? + var config = !deserializedManifest.Config.IsEmpty() ? new OciArtifactLayer(deserializedManifest.Config.Digest, deserializedManifest.Config.MediaType, await PullLayerAsync(client, deserializedManifest.Config)) : null; diff --git a/src/Bicep.Core/Registry/LocalModuleRegistry.cs b/src/Bicep.Core/Registry/LocalModuleRegistry.cs index b49a8e0a150..5f2de4402d5 100644 --- a/src/Bicep.Core/Registry/LocalModuleRegistry.cs +++ b/src/Bicep.Core/Registry/LocalModuleRegistry.cs @@ -2,17 +2,17 @@ // Licensed under the MIT License. using System.Diagnostics; +using System.IO.Abstractions; +using System.Runtime.InteropServices; using Bicep.Core.Diagnostics; +using Bicep.Core.Features; using Bicep.Core.FileSystem; using Bicep.Core.Modules; +using Bicep.Core.Registry.Oci; using Bicep.Core.Registry.Providers; using Bicep.Core.Semantics; using Bicep.Core.SourceCode; using Bicep.Core.Utils; -using System.IO.Abstractions; -using Bicep.Core.Features; -using Bicep.Core.Registry.Oci; -using System.Runtime.InteropServices; namespace Bicep.Core.Registry { @@ -80,7 +80,7 @@ public override ResultWithDiagnostic<Uri> TryGetLocalArtifactEntryPointUri(Local { if (reference.ArtifactType == ArtifactType.Provider) { - if (TryReadContent(reference) is not {} binaryData) + if (TryReadContent(reference) is not { } binaryData) { statuses.Add(reference, x => x.ArtifactRestoreFailedWithMessage(reference.FullyQualifiedReference, $"Failed to find {reference.FullyQualifiedReference}")); continue; @@ -152,12 +152,12 @@ protected override void WriteArtifactContentToCache(LocalModuleReference referen { if (entity.Provider.LocalDeployEnabled) { - if (SupportedArchitectures.TryGetCurrent() is not {} architecture) + if (SupportedArchitectures.TryGetCurrent() is not { } architecture) { throw new InvalidOperationException($"Unsupported architecture: {RuntimeInformation.ProcessArchitecture}"); } - if (entity.Provider.Binaries.SingleOrDefault(x => x.Architecture.Name == architecture.Name) is not {} binary) + if (entity.Provider.Binaries.SingleOrDefault(x => x.Architecture.Name == architecture.Name) is not { } binary) { throw new InvalidOperationException($"Unsupported architecture: {RuntimeInformation.ProcessArchitecture}"); } @@ -176,7 +176,7 @@ protected override void WriteArtifactContentToCache(LocalModuleReference referen protected override string GetArtifactDirectoryPath(LocalModuleReference reference) { - if (TryReadContent(reference) is not {} binaryData) + if (TryReadContent(reference) is not { } binaryData) { throw new InvalidOperationException($"Failed to resolve file path for {reference.FullyQualifiedReference}"); } @@ -193,21 +193,21 @@ protected override string GetArtifactDirectoryPath(LocalModuleReference referenc private BinaryData? TryReadContent(LocalModuleReference reference) { - if (FileResolver.TryResolveFilePath(reference.ParentModuleUri, reference.Path) is not {} fileUri || - FileResolver.TryReadAsBinaryData(fileUri).TryUnwrap() is not {} binaryData) + if (FileResolver.TryResolveFilePath(reference.ParentModuleUri, reference.Path) is not { } fileUri || + FileResolver.TryReadAsBinaryData(fileUri).TryUnwrap() is not { } binaryData) { return null; } return binaryData; } - + private Uri GetTypesTgzUri(LocalModuleReference reference) => GetFileUri(reference, "types.tgz"); private Uri GetProviderBinUri(LocalModuleReference reference) => GetFileUri(reference, "provider.bin"); protected override Uri GetArtifactLockFileUri(LocalModuleReference reference) => GetFileUri(reference, "lock"); - + private Uri GetFileUri(LocalModuleReference reference, string path) => new(FileSystem.Path.Combine(this.GetArtifactDirectoryPath(reference), path), UriKind.Absolute); } diff --git a/src/Bicep.Core/Registry/Oci/OciProvidersV1Config.cs b/src/Bicep.Core/Registry/Oci/OciProvidersV1Config.cs index ed3436192b5..cd82efae816 100644 --- a/src/Bicep.Core/Registry/Oci/OciProvidersV1Config.cs +++ b/src/Bicep.Core/Registry/Oci/OciProvidersV1Config.cs @@ -59,7 +59,8 @@ public static class SupportedArchitectures public static SupportedArchitecture? TryGetCurrent() { - return RuntimeInformation.ProcessArchitecture switch { + return RuntimeInformation.ProcessArchitecture switch + { Architecture.X64 when RuntimeInformation.IsOSPlatform(OSPlatform.Linux) => LinuxX64, Architecture.Arm64 when RuntimeInformation.IsOSPlatform(OSPlatform.Linux) => LinuxArm64, Architecture.X64 when RuntimeInformation.IsOSPlatform(OSPlatform.OSX) => OsxX64, @@ -69,4 +70,4 @@ Architecture.Arm64 when RuntimeInformation.IsOSPlatform(OSPlatform.Windows) => W _ => null, }; } -} \ No newline at end of file +} diff --git a/src/Bicep.Core/Registry/OciArtifactRegistry.cs b/src/Bicep.Core/Registry/OciArtifactRegistry.cs index 7e7f6664edd..5466b2caa1a 100644 --- a/src/Bicep.Core/Registry/OciArtifactRegistry.cs +++ b/src/Bicep.Core/Registry/OciArtifactRegistry.cs @@ -402,20 +402,20 @@ protected override void WriteArtifactContentToCache(OciArtifactReference referen if (result is OciProviderArtifactResult providerArtifact) { - var config = providerArtifact.Config is {} ? + var config = providerArtifact.Config is { } ? JsonSerializer.Deserialize(providerArtifact.Config.Data, OciProvidersV1ConfigSerializationContext.Default.OciProvidersV1Config) : null; // if the artifact supports local deployment, fetch the provider binary if (config?.LocalDeployEnabled == true) { - if (SupportedArchitectures.TryGetCurrent() is not {} architecture) + if (SupportedArchitectures.TryGetCurrent() is not { } architecture) { throw new InvalidOperationException($"Unsupported architecture: {RuntimeInformation.ProcessArchitecture}"); } var layerName = BicepMediaTypes.GetProviderArtifactLayerV1Binary(architecture); - if (result.TryGetSingleLayerByMediaType(layerName) is not {} sourceData) + if (result.TryGetSingleLayerByMediaType(layerName) is not { } sourceData) { throw new InvalidOperationException($"Unsupported architecture: {RuntimeInformation.ProcessArchitecture}"); } diff --git a/src/Bicep.Core/Registry/Providers/ProviderV1Archive.cs b/src/Bicep.Core/Registry/Providers/ProviderV1Archive.cs index 6915edaa3ec..0b5e1c3b6d1 100644 --- a/src/Bicep.Core/Registry/Providers/ProviderV1Archive.cs +++ b/src/Bicep.Core/Registry/Providers/ProviderV1Archive.cs @@ -52,7 +52,7 @@ public static ProviderPackage Read(BinaryData binaryData) binaries.Add(new(architecture, binary)); } } - + return new( Types: dataDict["types.tgz"], LocalDeployEnabled: binaries.Count != 0, diff --git a/src/Bicep.Local.Deploy.IntegrationTests/EndToEndDeploymentTests.cs b/src/Bicep.Local.Deploy.IntegrationTests/EndToEndDeploymentTests.cs index 1c78e5e0f53..edc8084d501 100644 --- a/src/Bicep.Local.Deploy.IntegrationTests/EndToEndDeploymentTests.cs +++ b/src/Bicep.Local.Deploy.IntegrationTests/EndToEndDeploymentTests.cs @@ -1,20 +1,20 @@ // Copyright (c) Microsoft Corporation. // Licensed under the MIT License. +using System.IO.Abstractions; +using Azure.Deployments.Core.Definitions; +using Azure.Deployments.Extensibility.Messages; using Bicep.Core.UnitTests; using Bicep.Core.UnitTests.Assertions; -using FluentAssertions; -using Microsoft.VisualStudio.TestTools.UnitTesting; -using Bicep.Local.Deploy.Extensibility; -using Bicep.Local.Deploy; +using Bicep.Core.UnitTests.Features; +using Bicep.Core.UnitTests.Mock; using Bicep.Core.UnitTests.Utils; -using Azure.Deployments.Core.Definitions; +using Bicep.Local.Deploy; +using Bicep.Local.Deploy.Extensibility; using Bicep.Local.Extension; +using FluentAssertions; +using Microsoft.VisualStudio.TestTools.UnitTesting; using Moq; -using Bicep.Core.UnitTests.Mock; -using Bicep.Core.UnitTests.Features; -using System.IO.Abstractions; -using Azure.Deployments.Extensibility.Messages; using Newtonsoft.Json.Linq; namespace Bicep.Local.Deploy.IntegrationTests; @@ -88,7 +88,8 @@ param coords { var providerMock = StrictMock.Of<LocalExtensibilityProvider>(); providerMock.Setup(x => x.Save(It.Is<ExtensibilityOperationRequest>(req => req.Resource.Properties["uri"]!.ToString() == "https://api.weather.gov/points/47.6363726,-122.1357068"), It.IsAny<CancellationToken>())) - .Returns<ExtensibilityOperationRequest, CancellationToken>((req, _) => { + .Returns<ExtensibilityOperationRequest, CancellationToken>((req, _) => + { req.Resource.Properties["body"] = """ { "properties": { @@ -102,7 +103,8 @@ param coords { return Task.FromResult<ExtensibilityOperationResponse>(new(req.Resource, null, null)); }); providerMock.Setup(x => x.Save(It.Is<ExtensibilityOperationRequest>(req => req.Resource.Properties["uri"]!.ToString() == "https://api.weather.gov/gridpoints/SEW/131,68/forecast"), It.IsAny<CancellationToken>())) - .Returns<ExtensibilityOperationRequest, CancellationToken>((req, _) => { + .Returns<ExtensibilityOperationRequest, CancellationToken>((req, _) => + { req.Resource.Properties["body"] = """ { "properties": { @@ -144,4 +146,4 @@ param coords { ] """)); } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy.IntegrationTests/KestrelProviderExtension.cs b/src/Bicep.Local.Deploy.IntegrationTests/KestrelProviderExtension.cs index 265652c3fb2..2806a705f99 100644 --- a/src/Bicep.Local.Deploy.IntegrationTests/KestrelProviderExtension.cs +++ b/src/Bicep.Local.Deploy.IntegrationTests/KestrelProviderExtension.cs @@ -2,13 +2,13 @@ // Licensed under the MIT License. using Bicep.Local.Extension; -using Bicep.Local.Extension.Rpc; using Bicep.Local.Extension.Protocol; -using Microsoft.VisualStudio.TestTools.UnitTesting; +using Bicep.Local.Extension.Rpc; using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Server.Kestrel.Core; using Microsoft.Extensions.DependencyInjection; +using Microsoft.VisualStudio.TestTools.UnitTesting; namespace Bicep.Local.Deploy.IntegrationTests; @@ -33,4 +33,4 @@ protected override async Task RunServer(string socketPath, ResourceDispatcher di await app.RunAsync(); } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy.IntegrationTests/ProviderExtensionTests.cs b/src/Bicep.Local.Deploy.IntegrationTests/ProviderExtensionTests.cs index 0cbb2fd3350..6076d7fc603 100644 --- a/src/Bicep.Local.Deploy.IntegrationTests/ProviderExtensionTests.cs +++ b/src/Bicep.Local.Deploy.IntegrationTests/ProviderExtensionTests.cs @@ -7,18 +7,18 @@ using Bicep.Core.UnitTests.Assertions; using Bicep.Core.UnitTests.Mock; using Bicep.Local.Extension; -using Bicep.Local.Extension.Rpc; using Bicep.Local.Extension.Protocol; +using Bicep.Local.Extension.Rpc; using FluentAssertions; +using Grpc.Core; using Microsoft.VisualStudio.TestTools.UnitTesting; using Microsoft.WindowsAzure.ResourceStack.Common.Json; using Moq; using Newtonsoft.Json; using Newtonsoft.Json.Linq; using Newtonsoft.Json.Serialization; -using Protocol = Bicep.Local.Extension.Protocol; using OmniSharp.Extensions.JsonRpc; -using Grpc.Core; +using Protocol = Bicep.Local.Extension.Protocol; namespace Bicep.Local.Deploy.IntegrationTests; @@ -64,7 +64,7 @@ public async Task Save_request_works_as_expected() handlerMock.SetupGet(x => x.ResourceType).Returns("apps/Deployment@v1"); handlerMock.Setup(x => x.Save(It.IsAny<Protocol.ExtensibilityOperationRequest>(), It.IsAny<CancellationToken>())) - .Returns<Protocol.ExtensibilityOperationRequest, CancellationToken>((req, _) => + .Returns<Protocol.ExtensibilityOperationRequest, CancellationToken>((req, _) => Task.FromResult(new Protocol.ExtensibilityOperationResponse(req.Resource, null, null))); await RunExtensionTest( @@ -73,7 +73,8 @@ await RunExtensionTest( { var request = new Extension.Rpc.ExtensibilityOperationRequest { - Import = new() { + Import = new() + { Provider = "Kubernetes", Version = "1.0.0", Config = """ @@ -83,7 +84,8 @@ await RunExtensionTest( } """ }, - Resource = new() { + Resource = new() + { Type = "apps/Deployment@v1", Properties = """ { diff --git a/src/Bicep.Local.Deploy/Extensibility/AzExtensibilityProvider.cs b/src/Bicep.Local.Deploy/Extensibility/AzExtensibilityProvider.cs index 6903a5f01df..5621d9ca6a8 100644 --- a/src/Bicep.Local.Deploy/Extensibility/AzExtensibilityProvider.cs +++ b/src/Bicep.Local.Deploy/Extensibility/AzExtensibilityProvider.cs @@ -42,31 +42,34 @@ public override async Task<ExtensibilityOperationResponse> Save(ExtensibilityOpe { switch (request.Resource.Type) { - case "Microsoft.Resources/deployments": { - var template = request.Resource.Properties["template"]!.ToString(); - var parameters = new JObject { - ["$schema"] = "https://schema.management.azure.com/schemas/2019-04-01/deploymentParameters.json#", - ["contentVersion"] = "1.0.0.0", - ["parameters"] = request.Resource.Properties["parameters"], - }; + case "Microsoft.Resources/deployments": + { + var template = request.Resource.Properties["template"]!.ToString(); + var parameters = new JObject + { + ["$schema"] = "https://schema.management.azure.com/schemas/2019-04-01/deploymentParameters.json#", + ["contentVersion"] = "1.0.0.0", + ["parameters"] = request.Resource.Properties["parameters"], + }; - var result = await LocalDeployment.Deploy(extensibilityHandler, template, parameters.ToJson(), cancellationToken); + var result = await LocalDeployment.Deploy(extensibilityHandler, template, parameters.ToJson(), cancellationToken); + + if (result.Deployment.Properties.ProvisioningState != ProvisioningState.Succeeded) + { + return new( + null, + null, + result.Deployment.Properties.Error.Details.SelectArray(x => new ExtensibilityError(x.Code, x.Message, x.Target))); + } - if (result.Deployment.Properties.ProvisioningState != ProvisioningState.Succeeded) - { return new( + new ExtensibleResourceData(request.Resource.Type, new JObject + { + ["outputs"] = result.Deployment.Properties.Outputs?.ToJToken(), + }), null, - null, - result.Deployment.Properties.Error.Details.SelectArray(x => new ExtensibilityError(x.Code, x.Message, x.Target))); + null); } - - return new( - new ExtensibleResourceData(request.Resource.Type, new JObject{ - ["outputs"] = result.Deployment.Properties.Outputs?.ToJToken(), - }), - null, - null); - } } throw new NotImplementedException(); diff --git a/src/Bicep.Local.Deploy/Extensibility/GrpcExtensibilityProvider.cs b/src/Bicep.Local.Deploy/Extensibility/GrpcExtensibilityProvider.cs index 8180f1e4f60..4ee61d8d84d 100644 --- a/src/Bicep.Local.Deploy/Extensibility/GrpcExtensibilityProvider.cs +++ b/src/Bicep.Local.Deploy/Extensibility/GrpcExtensibilityProvider.cs @@ -17,8 +17,8 @@ using Grpc.Net.Client; using Microsoft.WindowsAzure.ResourceStack.Common.Json; using Newtonsoft.Json.Linq; -using Messages = Azure.Deployments.Extensibility.Messages; using Data = Azure.Deployments.Extensibility.Data; +using Messages = Azure.Deployments.Extensibility.Messages; using Rpc = Bicep.Local.Extension.Rpc; namespace Bicep.Local.Deploy.Extensibility; @@ -56,7 +56,8 @@ public static async Task<LocalExtensibilityProvider> Start(Uri pathToBinary) }, }; - try { + try + { // 30s timeout for starting up the RPC connection var cts = new CancellationTokenSource(TimeSpan.FromSeconds(30)); @@ -76,7 +77,9 @@ public static async Task<LocalExtensibilityProvider> Start(Uri pathToBinary) await GrpcChannelHelper.WaitForConnectionAsync(client, cts.Token); return new GrpcExtensibilityProvider(client, process); - } catch (Exception ex) { + } + catch (Exception ex) + { await TerminateProcess(process); throw new InvalidOperationException($"Failed to connect to provider {pathToBinary.LocalPath}", ex); } @@ -103,13 +106,16 @@ public static async Task<LocalExtensibilityProvider> Start(Uri pathToBinary) } private static Rpc.ExtensibilityOperationRequest Convert(Messages.ExtensibilityOperationRequest request) - => new() { - Import = new Rpc.ExtensibleImportData { + => new() + { + Import = new Rpc.ExtensibleImportData + { Provider = request.Import.Provider, Version = request.Import.Version, Config = request.Import.Config?.ToJson(), }, - Resource = new Rpc.ExtensibleResourceData { + Resource = new Rpc.ExtensibleResourceData + { Type = request.Resource.Type, Properties = request.Resource.Properties?.ToJson(), }, @@ -117,9 +123,9 @@ private static Rpc.ExtensibilityOperationRequest Convert(Messages.ExtensibilityO private static Messages.ExtensibilityOperationResponse Convert(Rpc.ExtensibilityOperationResponse response) => new( - response.Resource is {} resource ? new(resource.Type, resource.Properties?.FromJson<JObject>()) : null, - response.ResourceMetadata is {} metadata ? new(metadata.ReadOnlyProperties.ToArray(), metadata.ImmutableProperties.ToArray(), metadata.DynamicProperties.ToArray()) : null, - response.Errors is {} errors ? errors.Select(error => new Data.ExtensibilityError(error.Code, error.Message, error.Target)).ToArray() : null); + response.Resource is { } resource ? new(resource.Type, resource.Properties?.FromJson<JObject>()) : null, + response.ResourceMetadata is { } metadata ? new(metadata.ReadOnlyProperties.ToArray(), metadata.ImmutableProperties.ToArray(), metadata.DynamicProperties.ToArray()) : null, + response.Errors is { } errors ? errors.Select(error => new Data.ExtensibilityError(error.Code, error.Message, error.Target)).ToArray() : null); public override async ValueTask DisposeAsync() { @@ -128,11 +134,14 @@ public override async ValueTask DisposeAsync() private static async Task TerminateProcess(Process process) { - try { + try + { var cts = new CancellationTokenSource(TimeSpan.FromSeconds(15)); await process.WaitForExitAsync(cts.Token); - } finally { + } + finally + { process.Kill(); } } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy/Extensibility/LocalExtensibilityHandler.cs b/src/Bicep.Local.Deploy/Extensibility/LocalExtensibilityHandler.cs index b8a57ed7865..a43ba44c771 100644 --- a/src/Bicep.Local.Deploy/Extensibility/LocalExtensibilityHandler.cs +++ b/src/Bicep.Local.Deploy/Extensibility/LocalExtensibilityHandler.cs @@ -68,8 +68,8 @@ public async Task<ExtensibilityOperationResponse> CallExtensibilityHost( foreach (var namespaceType in namespaceTypes) { - if (namespaceType.Artifact is {} artifact && - moduleDispatcher.TryGetProviderBinary(artifact) is {} binaryUri) + if (namespaceType.Artifact is { } artifact && + moduleDispatcher.TryGetProviderBinary(artifact) is { } binaryUri) { yield return (namespaceType, binaryUri); } @@ -89,7 +89,8 @@ public async Task InitializeProviders(Compilation compilation) public async ValueTask DisposeAsync() { - await Task.WhenAll(RegisteredProviders.Values.Select(async provider => { + await Task.WhenAll(RegisteredProviders.Values.Select(async provider => + { try { await provider.DisposeAsync(); diff --git a/src/Bicep.Local.Deploy/IServiceCollectionExtensions.cs b/src/Bicep.Local.Deploy/IServiceCollectionExtensions.cs index c5ea6f7011d..8f61d94f660 100644 --- a/src/Bicep.Local.Deploy/IServiceCollectionExtensions.cs +++ b/src/Bicep.Local.Deploy/IServiceCollectionExtensions.cs @@ -4,6 +4,7 @@ using System.Linq; using Azure.Deployments.Core.EventSources; using Azure.Deployments.Core.Exceptions; +using Azure.Deployments.Engine; using Azure.Deployments.Engine.Dependencies; using Azure.Deployments.Engine.Host.Azure; using Azure.Deployments.Engine.Host.Azure.Definitions; @@ -14,10 +15,11 @@ using Azure.Deployments.Engine.Host.Azure.Workers; using Azure.Deployments.Engine.Host.External; using Azure.Deployments.Engine.Interfaces; -using Azure.Deployments.Engine; using Azure.Deployments.Engine.Storage.Volatile; +using Azure.Deployments.Extensibility.Contract; using Azure.Deployments.Templates.Contracts; using Azure.Deployments.Templates.Export; +using Bicep.Local.Deploy.Extensibility; using Microsoft.Azure.Deployments.Service.Shared.Jobs; using Microsoft.Azure.Deployments.Shared.Host; using Microsoft.Extensions.DependencyInjection; @@ -25,8 +27,6 @@ using Microsoft.WindowsAzure.ResourceStack.Common.BackgroundJobs; using Microsoft.WindowsAzure.ResourceStack.Common.EventSources; using Microsoft.WindowsAzure.ResourceStack.Common.Storage.Volatile; -using Azure.Deployments.Extensibility.Contract; -using Bicep.Local.Deploy.Extensibility; namespace Bicep.Local.Deploy; diff --git a/src/Bicep.Local.Deploy/LocalDeployment.cs b/src/Bicep.Local.Deploy/LocalDeployment.cs index f68cbb63b53..75f4b17cc14 100644 --- a/src/Bicep.Local.Deploy/LocalDeployment.cs +++ b/src/Bicep.Local.Deploy/LocalDeployment.cs @@ -4,8 +4,8 @@ using System.Collections.Immutable; using System.Threading; using System.Threading.Tasks; -using Bicep.Local.Deploy.Extensibility; using Azure.Deployments.Core.Definitions; +using Bicep.Local.Deploy.Extensibility; using Microsoft.Azure.Deployments.Service.Shared.Jobs; using Microsoft.Extensions.DependencyInjection; @@ -22,7 +22,7 @@ public static async Task<Result> Deploy(LocalExtensibilityHandler extensibilityH var services = new ServiceCollection() .RegisterLocalDeployServices(extensibilityHandler) .BuildServiceProvider(); - + var engine = services.GetRequiredService<LocalDeploymentEngine>(); var dispatcher = services.GetRequiredService<WorkerJobDispatcherClient>(); @@ -35,4 +35,4 @@ public static async Task<Result> Deploy(LocalExtensibilityHandler extensibilityH await dispatcher.StopAsync(); } } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy/LocalDeploymentConfiguration.cs b/src/Bicep.Local.Deploy/LocalDeploymentConfiguration.cs index 5fabc1b9864..8d7b39ffd06 100644 --- a/src/Bicep.Local.Deploy/LocalDeploymentConfiguration.cs +++ b/src/Bicep.Local.Deploy/LocalDeploymentConfiguration.cs @@ -2,9 +2,9 @@ // Licensed under the MIT License. using Azure.Deployments.Core.Exceptions; +using Azure.Deployments.Engine; using Azure.Deployments.Engine.Dependencies; using Azure.Deployments.Engine.Host.Azure.Interfaces; -using Azure.Deployments.Engine; namespace Bicep.Local.Deploy; diff --git a/src/Bicep.Local.Deploy/LocalDeploymentEngine.cs b/src/Bicep.Local.Deploy/LocalDeploymentEngine.cs index 3b26f5ba74d..c2b1bada1f1 100644 --- a/src/Bicep.Local.Deploy/LocalDeploymentEngine.cs +++ b/src/Bicep.Local.Deploy/LocalDeploymentEngine.cs @@ -9,7 +9,6 @@ using System.Net; using System.Threading; using System.Threading.Tasks; -using Bicep.Local.Deploy.Extensibility; using Azure.Deployments.Core.Definitions; using Azure.Deployments.Core.Definitions.Schema; using Azure.Deployments.Core.Entities; @@ -23,6 +22,7 @@ using Azure.Deployments.Engine.Host.Azure.Interfaces; using Azure.Deployments.Engine.Interfaces; using Azure.Deployments.Templates.Engines; +using Bicep.Local.Deploy.Extensibility; using Microsoft.Azure.Deployments.Shared.Host; using Microsoft.WindowsAzure.ResourceStack.Common.BackgroundJobs.Exceptions; using Microsoft.WindowsAzure.ResourceStack.Common.Collections; @@ -186,4 +186,4 @@ await deploymentDataProvider.SaveDeployment( await deploymentStatusDataProvider.SaveDeploymentStatus( entity: statusEntity).ConfigureAwait(false); } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy/LocalDeploymentEngineHost.cs b/src/Bicep.Local.Deploy/LocalDeploymentEngineHost.cs index d25edfa8aac..3e2f2b75a03 100644 --- a/src/Bicep.Local.Deploy/LocalDeploymentEngineHost.cs +++ b/src/Bicep.Local.Deploy/LocalDeploymentEngineHost.cs @@ -9,7 +9,6 @@ using System.Net.Http.Headers; using System.Threading; using System.Threading.Tasks; -using Bicep.Local.Deploy.Extensibility; using Azure.Deployments.Core.Definitions; using Azure.Deployments.Core.Definitions.Identifiers; using Azure.Deployments.Core.Definitions.Resources; @@ -33,6 +32,7 @@ using Azure.Deployments.Engine.Interfaces; using Azure.Deployments.Extensibility.Messages; using Azure.Deployments.ResourceMetadata.Contracts; +using Bicep.Local.Deploy.Extensibility; using Microsoft.WindowsAzure.ResourceStack.Common.BackgroundJobs; using Microsoft.WindowsAzure.ResourceStack.Common.Extensions; using Microsoft.WindowsAzure.ResourceStack.Common.Instrumentation; @@ -165,10 +165,11 @@ public override void AddAsyncNotificationUri(HttpRequestHeaders httpHeaders, Bac => throw new NotImplementedException(); public override EnablementConfig GetEnablementConfig(PreviewDeploymentFunction feature) - => new() { + => new() + { FeatureName = feature.ToString() }; public override IResourceTypeMetadataProvider GetResourceTypeMetadataProvider() => throw new NotImplementedException(); -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Deploy/LocalRequestContext.cs b/src/Bicep.Local.Deploy/LocalRequestContext.cs index d46cb7885f0..b3ba6b466df 100644 --- a/src/Bicep.Local.Deploy/LocalRequestContext.cs +++ b/src/Bicep.Local.Deploy/LocalRequestContext.cs @@ -23,4 +23,4 @@ public LocalRequestContext() public string Location { get; } public string ApiVersion { get; } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension.Mock/Handlers/EchoResourceHandler.cs b/src/Bicep.Local.Extension.Mock/Handlers/EchoResourceHandler.cs index 335be520676..f1ab1e6fca7 100644 --- a/src/Bicep.Local.Extension.Mock/Handlers/EchoResourceHandler.cs +++ b/src/Bicep.Local.Extension.Mock/Handlers/EchoResourceHandler.cs @@ -37,7 +37,7 @@ public async Task<ExtensibilityOperationResponse> Save(ExtensibilityOperationReq var response = new ExtensibleResourceData( request.Resource.Type, JsonNode.Parse(JsonSerializer.Serialize(responseBody, SerializationContext.Default.EchoResponse))!.AsObject()); - + return new ExtensibilityOperationResponse(response, null, null); } } diff --git a/src/Bicep.Local.Extension.Mock/Program.cs b/src/Bicep.Local.Extension.Mock/Program.cs index 68be0332205..01c950e8ad9 100644 --- a/src/Bicep.Local.Extension.Mock/Program.cs +++ b/src/Bicep.Local.Extension.Mock/Program.cs @@ -2,10 +2,10 @@ // Licensed under the MIT License. using Bicep.Local.Extension; -using Bicep.Local.Extension.Rpc; -using Bicep.Local.Extension.Protocol; using Bicep.Local.Extension.Mock.Handlers; using Bicep.Local.Extension.Mock.Types; +using Bicep.Local.Extension.Protocol; +using Bicep.Local.Extension.Rpc; using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Server.Kestrel.Core; @@ -19,7 +19,7 @@ public static async Task Main(string[] args) { // hack to allow this extension to output types var typesOutputPath = Environment.GetEnvironmentVariable("MOCK_TYPES_OUTPUT_PATH"); - if (typesOutputPath is {}) + if (typesOutputPath is { }) { TypeGenerator.WriteTypes(typesOutputPath); return; @@ -54,4 +54,4 @@ protected override async Task RunServer(string socketPath, ResourceDispatcher di await app.RunAsync(); } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension.Mock/Types/TypesGenerator.cs b/src/Bicep.Local.Extension.Mock/Types/TypesGenerator.cs index 4284562679c..33bc68529bd 100644 --- a/src/Bicep.Local.Extension.Mock/Types/TypesGenerator.cs +++ b/src/Bicep.Local.Extension.Mock/Types/TypesGenerator.cs @@ -56,7 +56,8 @@ private static Dictionary<string, string> GenerateTypes() settings, null); - return new Dictionary<string, string>{ + return new Dictionary<string, string> + { ["index.json"] = GetString(stream => TypeSerializer.SerializeIndex(stream, index)), ["types.json"] = GetString(stream => TypeSerializer.Serialize(stream, factory.GetTypes())), }; @@ -75,4 +76,4 @@ public static void WriteTypes(string outdir) File.WriteAllText(filePath, contents); } } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension/Protocol/ResourceDispatcher.cs b/src/Bicep.Local.Extension/Protocol/ResourceDispatcher.cs index d04ae49b42f..3bba4880302 100644 --- a/src/Bicep.Local.Extension/Protocol/ResourceDispatcher.cs +++ b/src/Bicep.Local.Extension/Protocol/ResourceDispatcher.cs @@ -25,7 +25,7 @@ public IGenericResourceHandler GetHandler(string resourceType) return handler; } - if (this.genericResourceHandler is {}) + if (this.genericResourceHandler is { }) { return this.genericResourceHandler; } diff --git a/src/Bicep.Local.Extension/Protocol/ResourceDispatcherBuilder.cs b/src/Bicep.Local.Extension/Protocol/ResourceDispatcherBuilder.cs index 01bfd5835e5..f456ceedf1c 100644 --- a/src/Bicep.Local.Extension/Protocol/ResourceDispatcherBuilder.cs +++ b/src/Bicep.Local.Extension/Protocol/ResourceDispatcherBuilder.cs @@ -38,4 +38,4 @@ public ResourceDispatcher Build() this.genericResourceHandler, this.resourceHandlers.ToImmutableDictionary(StringComparer.OrdinalIgnoreCase)); } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension/ProviderExtension.cs b/src/Bicep.Local.Extension/ProviderExtension.cs index 07fd760d6f0..7d5d4f9b7b0 100644 --- a/src/Bicep.Local.Extension/ProviderExtension.cs +++ b/src/Bicep.Local.Extension/ProviderExtension.cs @@ -1,9 +1,9 @@ // Copyright (c) Microsoft Corporation. // Licensed under the MIT License. using System.Diagnostics; +using Bicep.Local.Extension.Protocol; using Bicep.Local.Extension.Rpc; using CommandLine; -using Bicep.Local.Extension.Protocol; namespace Bicep.Local.Extension; @@ -112,4 +112,4 @@ private static async Task RunWithCancellationAsync(Func<CancellationToken, Task> private static bool IsTracingEnabled => bool.TryParse(Environment.GetEnvironmentVariable("BICEP_TRACING_ENABLED"), out var value) && value; -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension/Rpc/BicepExtensionImpl.cs b/src/Bicep.Local.Extension/Rpc/BicepExtensionImpl.cs index 14dd7e09267..f680cdec326 100644 --- a/src/Bicep.Local.Extension/Rpc/BicepExtensionImpl.cs +++ b/src/Bicep.Local.Extension/Rpc/BicepExtensionImpl.cs @@ -1,3 +1,6 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. + using System.Linq; using System.Text.Json.Nodes; using Bicep.Local.Extension.Protocol; @@ -35,14 +38,14 @@ public override Task<Empty> Ping(Empty request, ServerCallContext context) private static Protocol.ExtensibilityOperationRequest Convert(ExtensibilityOperationRequest request) { return new( - new(request.Import.Provider, request.Import.Version, request.Import.Config is {} ? JsonNode.Parse(request.Import.Config) as JsonObject : null), - new(request.Resource.Type, request.Resource.Properties is {} ? JsonNode.Parse(request.Resource.Properties) as JsonObject : null)); + new(request.Import.Provider, request.Import.Version, request.Import.Config is { } ? JsonNode.Parse(request.Import.Config) as JsonObject : null), + new(request.Resource.Type, request.Resource.Properties is { } ? JsonNode.Parse(request.Resource.Properties) as JsonObject : null)); } private static ExtensibilityOperationResponse Convert(Protocol.ExtensibilityOperationResponse response) { var output = new ExtensibilityOperationResponse(); - if (response.Resource is {}) + if (response.Resource is { }) { output.Resource = new ExtensibleResourceData { @@ -51,14 +54,14 @@ private static ExtensibilityOperationResponse Convert(Protocol.ExtensibilityOper }; } - if (response.ResourceMetadata is {} metadata) + if (response.ResourceMetadata is { } metadata) { output.ResourceMetadata.ReadOnlyProperties.AddRange(metadata.ReadOnlyProperties); output.ResourceMetadata.ImmutableProperties.AddRange(metadata.ImmutableProperties); output.ResourceMetadata.DynamicProperties.AddRange(metadata.DynamicProperties); } - if (response.Errors is {} errors) + if (response.Errors is { } errors) { output.Errors.AddRange(errors.Select(error => new ExtensibilityError { @@ -73,7 +76,7 @@ private static ExtensibilityOperationResponse Convert(Protocol.ExtensibilityOper private static async Task<ExtensibilityOperationResponse> WrapExceptions(Func<Task<ExtensibilityOperationResponse>> func) { - try + try { return await func(); } @@ -86,8 +89,8 @@ private static async Task<ExtensibilityOperationResponse> WrapExceptions(Func<Ta Message = $"Rpc request failed: {ex}", Target = "" }); - + return response; } } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension/Rpc/GrpcChannelHelper.cs b/src/Bicep.Local.Extension/Rpc/GrpcChannelHelper.cs index 5c1d6ee0f01..0a43cbc8963 100644 --- a/src/Bicep.Local.Extension/Rpc/GrpcChannelHelper.cs +++ b/src/Bicep.Local.Extension/Rpc/GrpcChannelHelper.cs @@ -59,13 +59,16 @@ public static async Task WaitForConnectionAsync(BicepExtension.BicepExtensionCli var connected = false; while (!connected) { - try { + try + { await Task.Delay(50, cancellationToken); await client.PingAsync(new(), cancellationToken: cancellationToken); connected = true; - } catch (RpcException ex) when (ex.StatusCode == StatusCode.Unavailable) { + } + catch (RpcException ex) when (ex.StatusCode == StatusCode.Unavailable) + { // ignore } } } -} \ No newline at end of file +} diff --git a/src/Bicep.Local.Extension/TextWriterTraceListener.cs b/src/Bicep.Local.Extension/TextWriterTraceListener.cs index 1ac4a73ae25..ea537659aae 100644 --- a/src/Bicep.Local.Extension/TextWriterTraceListener.cs +++ b/src/Bicep.Local.Extension/TextWriterTraceListener.cs @@ -23,4 +23,4 @@ public override void WriteLine(string? message) { textWriter.WriteLine($"TRACE: {message}"); } -} \ No newline at end of file +}