Configure Serilog Elasticsearch in Blazor WebAssembly

偶尔善良 提交于 2020-08-26 09:54:29

问题


I'm currently working on a .NET Standard 2.1 Blazor WebAssembly hosted application. I use Serilog with ElasticSearch and want to send log messages from my Client project to the ElasticSearch server. My project structure looks like this:

  • BlazorApp.Client (I want to send logs to ElasticSearch from here)
  • BlazorApp.Server

A similar question is asked here: Serilog Not Logging to ElasticSearch in Blazor WebAssembly

I figured out how to send Logs using Serilogs .WriteTo.ElasticSearch() but I always run into an error on my browser console: Cannot Wait on monitors

Elasticsearch.Net.UnexpectedElasticsearchClientException: Cannot wait on monitors on this runtime. ---> System.Threading.SynchronizationLockException: Cannot wait on monitors on this runtime.

Reproduce:

I currently run ElasticStack on my localhost (ports :9200, :5601). First I needed to activate CORS on my ElasticSearch server, because the Blazor WASm application is a static web application. Thus I added the following code to my elasticsearch.yml:

http.cors.enabled : true
http.cors.allow-origin : "*"
http.cors.allow-methods : OPTIONS, HEAD, GET, POST, PUT, DELETE
http.cors.allow-headers : X-Requested-With,X-Auth-Token,Content-Type, Content-Length

Futher on, after doing some research on the the resulting errors in my browser console, I assumed that Serilogs NuGet Package Serilog.Sinks.Elasticsearch might not be production ready yet.

The reason is, that .WriteTo.Elasticsearch() is using an HttpClientHandler which is only partially supported in current Blazor WASm - as far as I know.

Thus I had to write my own HttpClientHandler implementation for Blazor WASm:

public class WasmHttpClientHandler : HttpClientHandler
{
    public override bool SupportsAutomaticDecompression => false;

    public override bool SupportsProxy => false;

    public override bool SupportsRedirectConfiguration => false;
}

The next step was to override the HttpConnection class of the Serilog NuGet package:

public class WasmHttpConnection : HttpConnection
{
    protected override HttpMessageHandler CreateHttpClientHandler(RequestData requestData)
    {
        var handler = new WasmHttpClientHandler();

        Func<object, X509Certificate, X509Chain, SslPolicyErrors, bool> callback = requestData.ConnectionSettings?.ServerCertificateValidationCallback;

        if (callback != null && handler.ServerCertificateCustomValidationCallback == null)
        {
            handler.ServerCertificateCustomValidationCallback = callback;
        }

        if (requestData.ClientCertificates != null)
        {
            handler.ClientCertificateOptions = ClientCertificateOption.Manual;
            handler.ClientCertificates.AddRange(requestData.ClientCertificates);
        }

        return handler;
    }
}

Then I needed to use this new connection:

return new ElasticsearchSinkOptions(new Uri("http://localhost:9200"))
           {
               IndexFormat = "test-index", 
               Connection = new WasmHttpConnection(),
           };

Main Method:

Log.Logger = new LoggerConfiguration()
             .Enrich.FromLogContext()
             .Enrich.WithMachineName()
             .Enrich.WithExceptionDetails()
             .WriteTo.Debug()
             .WriteTo.Console(new CompactJsonFormatter())
             .WriteTo.Elasticsearch(new ElasticsearchSinkOptions(new Uri("http://localhost:9200"))
           {
               IndexFormat = "test-index", 
               Connection = new WasmHttpConnection(),
           })
             .CreateLogger();

SelfLog.Enable(msg => Debug.WriteLine(msg));

With this setting, I can send my logs to my ElasticSearch and see the log messages in Kibana.

There is only one problem left, when I turn on Selflog on Serilog:

SelfLog.Enable(msg => Debug.WriteLine(msg));

I get the following error: Cannot wait on monitors. Which is also discussed here: Blazor WebAssembly Monitor Threading exception

This means, the Serilog .WriteTo.Elasticsearch() might not be production ready for Blazor WASm. Or perhaps you have an idea on how to improve my solution?

Please let me know if you have any better idea, a suggest on how to improve this solution or even a better working solution!

来源:https://stackoverflow.com/questions/63408984/configure-serilog-elasticsearch-in-blazor-webassembly

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!