private void Init(TOptions options)
        {
            Application.AddDefines(options.Defines);

            var projName      = Assembly.GetEntryAssembly().GetName().Name.Replace(".", " - ");
            var componentName = GetComponentName(options);

            Console.Title = $"{projName}, {componentName}";

            string logsDirectory =
                Path.GetFullPath(options.Log.IsNotEmptyString() ? options.Log : GetLogsDirectory(options));

            EventStoreLoggerConfiguration.Initialize(logsDirectory, componentName);

            Log.Information("\n{description,-25} {version} ({branch}/{hashtag}, {timestamp})", "ES VERSION:",
                            VersionInfo.Version, VersionInfo.Branch, VersionInfo.Hashtag, VersionInfo.Timestamp);
            Log.Information("{description,-25} {osFlavor} ({osVersion})", "OS:", OS.OsFlavor, Environment.OSVersion);
            Log.Information("{description,-25} {osRuntimeVersion} ({architecture}-bit)", "RUNTIME:",
                            OS.GetRuntimeVersion(),
                            Marshal.SizeOf(typeof(IntPtr)) * 8);
            Log.Information("{description,-25} {maxGeneration}", "GC:",
                            GC.MaxGeneration == 0
                                        ? "NON-GENERATION (PROBABLY BOEHM)"
                                        : $"{GC.MaxGeneration + 1} GENERATIONS");
            Log.Information("{description,-25} {logsDirectory}", "LOGS:", logsDirectory);

            Log.Information(EventStoreOptions.DumpOptions());

            if (options.WhatIf)
            {
                Application.Exit(ExitCode.Success, "WhatIf option specified");
            }
        }
예제 #2
0
        public static async Task <int> Main(bool version            = false, FileInfo?log              = null, bool whatIf             = false,
                                            string[]?command        = null, string host                = "localhost", int tcpPort      = 1113, int httpPort             = 2113,
                                            int timeout             = Timeout.Infinite, int readWindow = 2000, int writeWindow         = 2000, int pingWindow           = 2000,
                                            bool reconnect          = true, bool useTls                = false, bool tlsValidateServer = false, string connectionString = "",
                                            StatsFormat statsFormat = StatsFormat.Csv)
        {
            Log.Logger = EventStoreLoggerConfiguration.ConsoleLog;

            try {
                var logsDirectory = log?.FullName ?? Locations.DefaultTestClientLogDirectory;
                EventStoreLoggerConfiguration.Initialize(logsDirectory, "client", LogConsoleFormat.Plain,
                                                         1024 * 1024 * 1024, RollingInterval.Day, 31, false);
                var statsLog = statsFormat == StatsFormat.Csv
                                        ? TestClientCsvLoggerConfiguration.Initialize(logsDirectory, "client")
                                        : Log.ForContext(Serilog.Core.Constants.SourceContextPropertyName, "REGULAR-STATS-LOGGER");

                var options = new ClientOptions {
                    Timeout           = timeout,
                    HttpPort          = httpPort,
                    Host              = host,
                    TcpPort           = tcpPort,
                    Reconnect         = reconnect,
                    PingWindow        = pingWindow,
                    ReadWindow        = readWindow,
                    WriteWindow       = writeWindow,
                    UseTls            = useTls,
                    TlsValidateServer = tlsValidateServer,
                    ConnectionString  = connectionString,
                    Command           = command ?? Array.Empty <string>(),
                    OutputCsv         = statsFormat == StatsFormat.Csv,
                    StatsLog          = statsLog
                };

                var hostedService = new TestClientHostedService(options);

                if (whatIf)
                {
                    await Console.Out.WriteLineAsync(options.ToString());
                }

                if (version || whatIf)
                {
                    await Console.Out.WriteLineAsync(VersionInfo.Text);

                    await Console.Out.FlushAsync();

                    return(0);
                }
                await CreateHostBuilder(hostedService, Environment.GetCommandLineArgs())
                .RunConsoleAsync(options => options.SuppressStatusMessages = true, hostedService.CancellationToken);

                return(await hostedService.Exited);
            } catch (Exception ex) {
                Log.Fatal(ex, "Host terminated unexpectedly.");
                return(1);
            } finally {
                Log.CloseAndFlush();
            }
        }
예제 #3
0
 protected override void Init(ClusterNodeOptions options)
 {
     base.Init(options);
     if (options.LogLevel != LogLevel.Default)
     {
         EventStoreLoggerConfiguration.AdjustMinimumLogLevel(options.LogLevel);
     }
 }
예제 #4
0
        public static async Task <int> Main(string[] args)
        {
            ThreadPool.SetMaxThreads(1000, 1000);
            ClusterVNodeOptions options;
            var exitCodeSource = new TaskCompletionSource <int>();
            var cts            = new CancellationTokenSource();

            Log.Logger = EventStoreLoggerConfiguration.ConsoleLog;
            try {
                try {
                    options = ClusterVNodeOptions.FromConfiguration(args, Environment.GetEnvironmentVariables());
                } catch (Exception ex) {
                    Log.Fatal($"Error while parsing options: {ex.Message}");
                    Log.Information($"Options:{Environment.NewLine}{ClusterVNodeOptions.HelpText}");

                    return(1);
                }

                var logsDirectory = string.IsNullOrWhiteSpace(options.Log.Log)
                                        ? Locations.DefaultLogDirectory
                                        : options.Log.Log;
                EventStoreLoggerConfiguration.Initialize(logsDirectory, options.GetComponentName(),
                                                         options.Log.LogConsoleFormat,
                                                         options.Log.LogFileSize,
                                                         options.Log.LogFileInterval,
                                                         options.Log.LogFileRetentionCount,
                                                         options.Log.DisableLogFile,
                                                         options.Log.LogConfig);

                if (options.Application.Help)
                {
                    await Console.Out.WriteLineAsync(ClusterVNodeOptions.HelpText);

                    return(0);
                }

                if (options.Application.Version)
                {
                    await Console.Out.WriteLineAsync(VersionInfo.Text);

                    return(0);
                }

                Log.Information("\n{description,-25} {version} ({branch}/{hashtag}, {timestamp})", "ES VERSION:",
                                VersionInfo.Version, VersionInfo.Branch, VersionInfo.Hashtag, VersionInfo.Timestamp);
                Log.Information("{description,-25} {osFlavor} ({osVersion})", "OS:", OS.OsFlavor,
                                Environment.OSVersion);
                Log.Information("{description,-25} {osRuntimeVersion} ({architecture}-bit)", "RUNTIME:",
                                OS.GetRuntimeVersion(),
                                Marshal.SizeOf(typeof(IntPtr)) * 8);
                Log.Information("{description,-25} {maxGeneration}", "GC:",
                                GC.MaxGeneration == 0
                                                ? "NON-GENERATION (PROBABLY BOEHM)"
                                                : $"{GC.MaxGeneration + 1} GENERATIONS");
                Log.Information("{description,-25} {logsDirectory}", "LOGS:", logsDirectory);
                Log.Information(options.DumpOptions());

                var deprecationWarnings = options.GetDeprecationWarnings();
                if (deprecationWarnings != null)
                {
                    Log.Warning($"DEPRECATED{Environment.NewLine}{deprecationWarnings}");
                }

                if (options.Application.Insecure)
                {
                    Log.Warning(
                        "\n==============================================================================================================\n" +
                        "INSECURE MODE IS ON. THIS MODE IS *NOT* RECOMMENDED FOR PRODUCTION USE.\n" +
                        "INSECURE MODE WILL DISABLE ALL AUTHENTICATION, AUTHORIZATION AND TRANSPORT SECURITY FOR ALL CLIENTS AND NODES.\n" +
                        "==============================================================================================================\n");
                }

                if (!options.Cluster.DiscoverViaDns && options.Cluster.GossipSeed.Length == 0 &&
                    options.Cluster.ClusterSize == 1)
                {
                    Log.Information(
                        "DNS discovery is disabled, but no gossip seed endpoints have been specified. Since "
                        + "the cluster size is set to 1, this may be intentional. Gossip seeds can be specified "
                        + "using the `GossipSeed` option.");
                }

                if (options.Application.WhatIf)
                {
                    return(0);
                }

                Application.RegisterExitAction(code => {
                    cts.Cancel();
                    exitCodeSource.SetResult(code);
                });

                Console.CancelKeyPress += delegate {
                    Application.Exit(0, "Cancelled.");
                };
                using (var hostedService = new ClusterVNodeHostedService(options)) {
                    using var signal = new ManualResetEventSlim(false);
                    _ = Run(hostedService, signal);
                    // ReSharper disable MethodSupportsCancellation
                    signal.Wait();
                    // ReSharper restore MethodSupportsCancellation
                }

                return(await exitCodeSource.Task);

                async Task Run(ClusterVNodeHostedService hostedService, ManualResetEventSlim signal)
                {
                    try {
                        await new HostBuilder()
                        .ConfigureHostConfiguration(builder =>
                                                    builder.AddEnvironmentVariables("DOTNET_").AddCommandLine(args))
                        .ConfigureAppConfiguration(builder =>
                                                   builder.AddEnvironmentVariables().AddCommandLine(args))
                        .ConfigureServices(services => services.AddSingleton <IHostedService>(hostedService))
                        .ConfigureLogging(logging => logging.AddSerilog())
                        .ConfigureServices(services => services.Configure <KestrelServerOptions>(
                                               EventStoreKestrelConfiguration.GetConfiguration()))
                        .ConfigureWebHostDefaults(builder => builder
                                                  .UseKestrel(server => {
                            server.Limits.Http2.KeepAlivePingDelay =
                                TimeSpan.FromMilliseconds(options.Grpc.KeepAliveInterval);
                            server.Limits.Http2.KeepAlivePingTimeout =
                                TimeSpan.FromMilliseconds(options.Grpc.KeepAliveTimeout);
                            server.Listen(options.Interface.ExtIp, options.Interface.HttpPort,
                                          listenOptions => {
                                if (hostedService.Node.DisableHttps)
                                {
                                    listenOptions.Use(next =>
                                                      new ClearTextHttpMultiplexingMiddleware(next).OnConnectAsync);
                                }
                                else
                                {
                                    listenOptions.UseHttps(new HttpsConnectionAdapterOptions {
                                        ServerCertificateSelector = delegate {
                                            return(hostedService.Node.CertificateSelector());
                                        },
                                        ClientCertificateMode       = ClientCertificateMode.AllowCertificate,
                                        ClientCertificateValidation = (certificate, chain, sslPolicyErrors) => {
                                            var(isValid, error) =
                                                hostedService.Node.InternalClientCertificateValidator(
                                                    certificate,
                                                    chain,
                                                    sslPolicyErrors);
                                            if (!isValid && error != null)
                                            {
                                                Log.Error("Client certificate validation error: {e}", error);
                                            }

                                            return(isValid);
                                        }
                                    });
                                }
                            });
                        })
                                                  .ConfigureServices(services => hostedService.Node.Startup.ConfigureServices(services))
                                                  .Configure(hostedService.Node.Startup.Configure))
                        .RunConsoleAsync(options => options.SuppressStatusMessages = true, cts.Token);
                    } catch (Exception ex) {
                        Log.Fatal("Error occurred during setup: {e}", ex);
                        exitCodeSource.TrySetResult(1);
                    } finally {
                        signal.Set();
                    }
                }
            } catch (InvalidConfigurationException ex) {
                Log.Fatal("Invalid Configuration: " + ex.Message);
                return(1);
            }
            catch (Exception ex) {
                Log.Fatal(ex, "Host terminated unexpectedly.");
                return(1);
            } finally {
                Log.CloseAndFlush();
            }
        }