diff --git a/src/Microsoft.Tye.Core/ExtensionContext.cs b/src/Microsoft.Tye.Core/ExtensionContext.cs index 42ca7b75..cfe616d3 100644 --- a/src/Microsoft.Tye.Core/ExtensionContext.cs +++ b/src/Microsoft.Tye.Core/ExtensionContext.cs @@ -6,15 +6,18 @@ namespace Microsoft.Tye { public sealed class ExtensionContext { - public ExtensionContext(ApplicationBuilder application, OutputContext output, OperationKind operation) + public ExtensionContext(ApplicationBuilder application, HostOptions? options, OutputContext output, OperationKind operation) { Application = application; + Options = options; Output = output; Operation = operation; } public ApplicationBuilder Application { get; } + public HostOptions? Options { get; } + public OutputContext Output { get; } public OperationKind Operation { get; } diff --git a/src/Microsoft.Tye.Hosting/HostOptions.cs b/src/Microsoft.Tye.Core/HostOptions.cs similarity index 67% rename from src/Microsoft.Tye.Hosting/HostOptions.cs rename to src/Microsoft.Tye.Core/HostOptions.cs index d7439c26..69783fec 100644 --- a/src/Microsoft.Tye.Hosting/HostOptions.cs +++ b/src/Microsoft.Tye.Core/HostOptions.cs @@ -3,9 +3,8 @@ // See the LICENSE file in the project root for more information. using System.Collections.Generic; -using Microsoft.Tye.Hosting.Diagnostics; -namespace Microsoft.Tye.Hosting +namespace Microsoft.Tye { public class HostOptions { @@ -13,10 +12,14 @@ namespace Microsoft.Tye.Hosting public List Debug { get; } = new List(); - public DiagnosticOptions Diagnostics { get; } = new DiagnosticOptions(); + public (string Key, string Value) DistributedTraceProvider { get; set; } public bool Docker { get; set; } + public (string Key, string Value) LoggingProvider { get; set; } + + public (string Key, string Value) MetricsProvider { get; set; } + public bool NoBuild { get; set; } public int? Port { get; set; } diff --git a/src/Microsoft.Tye.Extensions/Zipkin/ZipkinExtension.cs b/src/Microsoft.Tye.Extensions/Zipkin/ZipkinExtension.cs index 063ab2de..533a39c8 100644 --- a/src/Microsoft.Tye.Extensions/Zipkin/ZipkinExtension.cs +++ b/src/Microsoft.Tye.Extensions/Zipkin/ZipkinExtension.cs @@ -14,27 +14,49 @@ namespace Microsoft.Tye.Extensions.Zipkin { public override Task ProcessAsync(ExtensionContext context, ExtensionConfiguration config) { - if (context.Application.Services.Any(s => s.Name == "zipkin")) - { - context.Output.WriteDebugLine("Zipkin service already configured. Skipping..."); - return Task.CompletedTask; - } - if (context.Operation == ExtensionContext.OperationKind.LocalRun) { - var service = new ContainerServiceBuilder("zipkin", "openzipkin/zipkin") + if (context.Application.Services.Any(s => s.Name == "zipkin")) { - Bindings = + context.Output.WriteDebugLine("zipkin service already configured. Skipping..."); + } + else + { + context.Output.WriteDebugLine("Injecting zipkin service..."); + + var service = new ContainerServiceBuilder("zipkin", "openzipkin/zipkin") { - new BindingBuilder() + Bindings = { - Port = 9411, - ContainerPort = 9411, - Protocol = "http", + new BindingBuilder() + { + Port = 9411, + ContainerPort = 9411, + Protocol = "http", + }, }, - }, - }; - context.Application.Services.Add(service); + }; + context.Application.Services.Add(service); + + foreach (var s in context.Application.Services) + { + if (object.ReferenceEquals(s, service)) + { + continue; + } + + // make zipkin available as a dependency of everything. + if (!s.Dependencies.Contains(service.Name)) + { + s.Dependencies.Add(service.Name); + } + } + } + + if (context.Options!.DistributedTraceProvider.Key is null) + { + context.Options.DistributedTraceProvider = ("zipkin", "http://localhost:9411"); + } } return Task.CompletedTask; diff --git a/src/Microsoft.Tye.Hosting/TyeHost.cs b/src/Microsoft.Tye.Hosting/TyeHost.cs index 67925db2..b1fd4762 100644 --- a/src/Microsoft.Tye.Hosting/TyeHost.cs +++ b/src/Microsoft.Tye.Hosting/TyeHost.cs @@ -248,10 +248,17 @@ namespace Microsoft.Tye.Hosting private static AggregateApplicationProcessor CreateApplicationProcessor(ReplicaRegistry replicaRegistry, HostOptions options, Microsoft.Extensions.Logging.ILogger logger) { - var diagnosticsCollector = new DiagnosticsCollector(logger, options.Diagnostics); + var diagnostics = new DiagnosticOptions() + { + DistributedTraceProvider = options.DistributedTraceProvider, + LoggingProvider = options.LoggingProvider, + MetricsProvider = options.MetricsProvider, + }; + + var diagnosticsCollector = new DiagnosticsCollector(logger, diagnostics); // Print out what providers were selected and their values - options.Diagnostics.DumpDiagnostics(logger); + diagnostics.DumpDiagnostics(logger); var processors = new List { diff --git a/src/tye/ApplicationBuilderExtensions.cs b/src/tye/ApplicationBuilderExtensions.cs index e8c351a2..677ed351 100644 --- a/src/tye/ApplicationBuilderExtensions.cs +++ b/src/tye/ApplicationBuilderExtensions.cs @@ -14,7 +14,7 @@ namespace Microsoft.Tye { // For layering reasons this has to live in the `tye` project. We don't want to leak // the extensions themselves into Tye.Core. - public static async Task ProcessExtensionsAsync(this ApplicationBuilder application, OutputContext output, ExtensionContext.OperationKind operation) + public static async Task ProcessExtensionsAsync(this ApplicationBuilder application, HostOptions? options, OutputContext output, ExtensionContext.OperationKind operation) { foreach (var extensionConfig in application.Extensions) { @@ -23,7 +23,7 @@ namespace Microsoft.Tye throw new CommandException($"Could not find the extension '{extensionConfig.Name}'."); } - var context = new ExtensionContext(application, output, operation); + var context = new ExtensionContext(application, options, output, operation); await extension.ProcessAsync(context, extensionConfig); } } diff --git a/src/tye/BuildHost.cs b/src/tye/BuildHost.cs index ffccc91f..1d0a67d1 100644 --- a/src/tye/BuildHost.cs +++ b/src/tye/BuildHost.cs @@ -25,7 +25,7 @@ namespace Microsoft.Tye public static async Task ExecuteBuildAsync(OutputContext output, ApplicationBuilder application, string environment, bool interactive) { - await application.ProcessExtensionsAsync(output, ExtensionContext.OperationKind.Deploy); + await application.ProcessExtensionsAsync(options: null, output, ExtensionContext.OperationKind.Deploy); Program.ApplyRegistry(output, application, interactive, requireRegistry: false); var executor = new ApplicationExecutor(output) diff --git a/src/tye/GenerateHost.cs b/src/tye/GenerateHost.cs index 3490c1b6..a336e82a 100644 --- a/src/tye/GenerateHost.cs +++ b/src/tye/GenerateHost.cs @@ -32,7 +32,7 @@ namespace Microsoft.Tye public static async Task ExecuteGenerateAsync(OutputContext output, ApplicationBuilder application, string environment, bool interactive) { - await application.ProcessExtensionsAsync(output, ExtensionContext.OperationKind.Deploy); + await application.ProcessExtensionsAsync(options: null, output, ExtensionContext.OperationKind.Deploy); Program.ApplyRegistry(output, application, interactive, requireRegistry: false); var executor = new ApplicationExecutor(output) diff --git a/src/tye/Program.DeployCommand.cs b/src/tye/Program.DeployCommand.cs index 05beaada..769b2954 100644 --- a/src/tye/Program.DeployCommand.cs +++ b/src/tye/Program.DeployCommand.cs @@ -69,7 +69,7 @@ namespace Microsoft.Tye throw new CommandException($"Cannot apply manifests because kubectl is not connected to a cluster."); } - await application.ProcessExtensionsAsync(output, ExtensionContext.OperationKind.Deploy); + await application.ProcessExtensionsAsync(options: null, output, ExtensionContext.OperationKind.Deploy); ApplyRegistry(output, application, interactive, requireRegistry: true); var executor = new ApplicationExecutor(output) diff --git a/src/tye/Program.PushCommand.cs b/src/tye/Program.PushCommand.cs index 2a2bd743..f17507a8 100644 --- a/src/tye/Program.PushCommand.cs +++ b/src/tye/Program.PushCommand.cs @@ -51,7 +51,7 @@ namespace Microsoft.Tye private static async Task ExecutePushAsync(OutputContext output, ApplicationBuilder application, string environment, bool interactive, bool force) { - await application.ProcessExtensionsAsync(output, ExtensionContext.OperationKind.Deploy); + await application.ProcessExtensionsAsync(options: null, output, ExtensionContext.OperationKind.Deploy); ApplyRegistry(output, application, interactive, requireRegistry: true); var executor = new ApplicationExecutor(output) diff --git a/src/tye/Program.RunCommand.cs b/src/tye/Program.RunCommand.cs index d9bfe1e7..e2da46c2 100644 --- a/src/tye/Program.RunCommand.cs +++ b/src/tye/Program.RunCommand.cs @@ -92,13 +92,6 @@ namespace Microsoft.Tye throw new CommandException($"No services found in \"{application.Source.Name}\""); } - await application.ProcessExtensionsAsync(output, ExtensionContext.OperationKind.LocalRun); - - InitializeThreadPoolSettings(application.Services.Count); - - output.WriteInfoLine("Launching Tye Host..."); - output.WriteInfoLine(string.Empty); - var options = new HostOptions() { Dashboard = args.Dashboard, @@ -106,15 +99,19 @@ namespace Microsoft.Tye NoBuild = args.NoBuild, Port = args.Port, - Diagnostics = - { - DistributedTraceProvider = DiagnosticOptions.GetProvider(args.Dtrace), - LoggingProvider = DiagnosticOptions.GetProvider(args.Logs), - MetricsProvider = DiagnosticOptions.GetProvider(args.Metrics), - }, + DistributedTraceProvider = DiagnosticOptions.GetProvider(args.Dtrace), + LoggingProvider = DiagnosticOptions.GetProvider(args.Logs), + MetricsProvider = DiagnosticOptions.GetProvider(args.Metrics), }; options.Debug.AddRange(args.Debug); + await application.ProcessExtensionsAsync(options, output, ExtensionContext.OperationKind.LocalRun); + + InitializeThreadPoolSettings(application.Services.Count); + + output.WriteInfoLine("Launching Tye Host..."); + output.WriteInfoLine(string.Empty); + await using var host = new TyeHost(application.ToHostingApplication(), options); await host.RunAsync(); });