Beispiel #1
0
 private int OnExecute(CommandLineApplication app, IConsole console)
 {
     EGBenchLogger.WriteLine(console, "You must specify a subcommand.");
     console.WriteLine();
     app.ShowHelp();
     return(1);
 }
Beispiel #2
0
 public void Configure(IApplicationBuilder app)
 {
     app.Use(async(HttpContext ctx, Func <Task> next) =>
     {
         try
         {
             await next();
         }
         catch (Exception ex)
         {
             EGBenchLogger.WriteLine(ex.ToString());
             throw;
         }
     });
     app.Run(this.RequestHandlerAsync);
 }
Beispiel #3
0
        private void Validate(IConsole console)
        {
            string serialized;
            int    bytesLength;

            using (var ms = new MemoryStream())
                using (var content = (EventGridAndCloudEventHttpContent)this.CreateHttpContent())
                {
                    content.SerializeToStreamAsync(ms).GetAwaiter().GetResult();
                    byte[] bytes = ms.ToArray();
                    bytesLength = bytes.Length;
                    serialized  = Encoding.UTF8.GetString(ms.ToArray());
                }

            EGBenchLogger.WriteLine(console, $"Sample request payload that'll get sent out: Size={bytesLength} Actual payload=\n{serialized}");
            _ = JsonSerializer.Deserialize <EventGridEvent[]>(serialized);
        }
Beispiel #4
0
                private static TaskCompletionSource <int> CreateTcs(CancellationTokenSource stopHostCts, IWebHost host, IConsole console, int runtimeInMinutes)
                {
                    var tcs = new TaskCompletionSource <int>();

                    if (runtimeInMinutes > 0)
                    {
                        // on runtime expiry, signal stopHostCts and tcs
                        _ = Task.Delay(TimeSpan.FromMinutes(runtimeInMinutes)).ContinueWith(
                            t =>
                        {
                            EGBenchLogger.WriteLine(console, $"--runtime-in-minutes ({runtimeInMinutes}) Minutes have passed, shutting down publishers.");
                            try
                            {
                                stopHostCts.Cancel();
                                tcs.TrySetResult(0);
                            }
                            catch (Exception ex)
                            {
                                tcs.TrySetException(ex);
                            }
                        },
                            TaskScheduler.Default);
                    }

                    // on host shutdown, signal tcs
                    _ = host.WaitForShutdownAsync().ContinueWith(
                        t =>
                    {
                        if (t.IsFaulted)
                        {
                            tcs.TrySetException(t.Exception);
                        }
                        else
                        {
                            tcs.TrySetResult(0);
                        }
                    },
                        TaskScheduler.Default);

                    return(tcs);
                }
Beispiel #5
0
            static async Task ReportingLoop(IMetricsRoot @metrics, int metricsIntervalSeconds)
            {
                Timestamp lastStartTime = Timestamp.Now;

                while (true)
                {
                    int waitInSeconds = Math.Clamp(metricsIntervalSeconds - (int)lastStartTime.ElapsedSeconds, 0, metricsIntervalSeconds);
                    if (waitInSeconds > 0)
                    {
                        await Task.Delay(waitInSeconds * 1000);
                    }

                    lastStartTime = Timestamp.Now;
                    try
                    {
                        await Task.WhenAll(@metrics.ReportRunner.RunAllAsync(CancellationToken.None));
                    }
                    catch (Exception ex)
                    {
                        EGBenchLogger.WriteLine($"Metrics reporting exception: {ex.Message}");
                    }
                }
            }
Beispiel #6
0
        private static void Initialize(CLI root)
        {
            if (root == null)
            {
                throw new InvalidOperationException("root should not be null.");
            }

            string context = root.RunTag ?? nameof(EGBench);

            IMetricsBuilder builder = AppMetrics.CreateDefaultBuilder()
                                      .Filter.With(new MetricsFilter().WhereContext(context))
                                      .Configuration.Configure(options =>
            {
                options.DefaultContextLabel = context;
                options.GlobalTags.Clear();
                options.Enabled          = true;
                options.ReportingEnabled = true;
            });

            if (root.AppInsightsKey.HasValue)
            {
                EGBenchLogger.WriteLine($"Reporting metrics to application insights with instrumentation key={root.AppInsightsKey.Value}");
                builder.Report.ToApplicationInsights(root.AppInsightsKey.Value);
            }
            else
            {
                isConsole = true;
                EGBenchLogger.WriteLine("Reporting metrics to console since --app-insights-key was not specified.");
                builder.Report.ToConsole(options =>
                {
                    options.MetricsOutputFormatter = new MetricsInfluxDbLineProtocolOutputFormatter();
                });
            }

            metricsRoot = builder.Build();

            _ = Task.Run(() => ReportingLoop(metricsRoot, root.MetricsIntervalSeconds));
Beispiel #7
0
                public async Task <int> OnExecuteAsync(CommandLineApplication app, IConsole console)
                {
                    this.LogOptionValues(console);
                    this.Root.LogOptionValues(console);

                    this.StatusCodeMap = this.ReturnStatusCodes
                                         .Select((s, i) =>
                    {
                        string s2    = s.Trim();
                        string[] ss  = s2.Split(',', ';', ' ', '|', '_', ':');
                        string error = string.Empty;
                        if (ss.Length != 2)
                        {
                            error = $"--return-code at index {i} with string value of '{s}' is invalid. Valid examples: -r \"10,400\" -r \"90:200\"";
                        }
                        else if (!int.TryParse(ss[0].Trim(), out int percent))
                        {
                            error = $"--return-code at index {i} with string value of '{s}' has a percentage value that can't be parsed to an integer.";
                        }
                        else if (!Enum.TryParse <HttpStatusCode>(ss[1].Trim(), out HttpStatusCode statusCode))
                        {
                            error = $"--return-code at index {i} with string value of '{s}' has a http status code value that can't be parsed to the HttpStatusCode type.";
                        }
                        else
                        {
                            return(percent, statusCode);
                        }

                        throw new InvalidOperationException(error);
                    })
                                         .ToArray();

                    if (this.StatusCodeMap.Sum(kvp => kvp.percent) != 100)
                    {
                        throw new InvalidOperationException($"Sum of all percentages should be 100, was found to be {this.StatusCodeMap.Sum(kvp => kvp.percent)}. Parsed percentages={string.Join(',', this.StatusCodeMap.Select(kvp => kvp.percent))}");
                    }

                    EGBenchLogger.WriteLine($"Parsed status code map:\n{string.Join("\n", this.StatusCodeMap.Select(kvp => $"{kvp.percent}% HTTP {kvp.statusCode}").ToArray())}");

                    Metric.InitializeSubscriber(this.Root);

                    this.host = new WebHostBuilder()
                                .UseContentRoot(Directory.GetCurrentDirectory())
                                .UseKestrel(options =>
                    {
                        options.ListenAnyIP(this.Port);
                        options.Limits.MinRequestBodyDataRate = null;
                        options.Limits.MinResponseDataRate    = null;
                        // options.AllowSynchronousIO = true;
                    })
                                .ConfigureServices(services =>
                    {
                        services.AddSingleton <StartListenerCommand>(this);
                    })
                                .ConfigureLogging(lb =>
                    {
                        lb.SetMinimumLevel(LogLevel.Warning);
                        lb.AddConsole();
                    })
                                .UseStartup <ListenerStartup>()
                                .Build();

                    using (var stopHostCts = new CancellationTokenSource())
                    {
                        await this.host.StartAsync(stopHostCts.Token);

                        TaskCompletionSource <int> tcs = CreateTcs(stopHostCts, this.host, console, this.RuntimeInMinutes);
                        string endpointUrl             = this.host.ServerFeatures.Get <IServerAddressesFeature>().Addresses.First(s => s.StartsWith("http://", StringComparison.OrdinalIgnoreCase));
                        EGBenchLogger.WriteLine(console, $"Started webserver at {endpointUrl}");
                        int result = await tcs.Task;
                        return(result);
                    }
                }
Beispiel #8
0
 public static void LogOptionValues(this object @this, IConsole console)
 {
     PropertyInfo[] options = @this.GetType().GetProperties(BindingFlags.Public | BindingFlags.Instance).Where(p => p.GetCustomAttribute <OptionAttribute>() != null).ToArray();
     EGBenchLogger.WriteLine(console, $"Commandline arguments (merged from cmdline and code defaults):\n{string.Join("\n", options.Select(o => $"{o.Name}={ToString(o.GetValue(@this))}"))}");