Exceptionless - .Net Core開源日誌框架(二)

後臺運行服務

上次我就是直接通過腳本Start-ElasticSearch.ps1啟動ElasticSearch和Kibana服務,但是大家也能看到,服務是運行起來了,同時還有兩個命令窗口,如果一個不小心把窗口關閉了,服務也就關閉了,而且一旦服務器重啟了,這兩個服務也不會自動啟動。我這裡先暫時把Kibana扔一邊去,來看看ElasticSearch服務。ElasticSearch是直接有腳本支持將ElasticSearch安裝為Windows服務,在後臺運行。

Exceptionless - .Net Core開源日誌框架(二)

就是這個elasticsearch-service.bat腳本,支持一下參數:

  • install 將Elasticsearch作為服務安裝
  • remove 刪除已安裝的Elasticsearch服務(並在啟動時停止服務)
  • start 啟動Elasticsearch服務(如果已安裝)
  • stop 停止Elasticsearch服務(如果啟動)
  • manager 啟動一個GUI來管理已安裝的服務

安裝命令行,進入到elasticsearch-service.bat所在的目錄,然後執行下面的腳本

<code>elasticsearch-service.bat install
/<code>

啟動

Exceptionless - .Net Core開源日誌框架(二)

這個時候我們可以直接在瀏覽器訪問9200端口看看服務是否正常

Exceptionless - .Net Core開源日誌框架(二)

繼續使用上次部署好的Exceptionless(如何使用IIS部署Exceptionless Web服務,請看Exceptionless - .Net Core開源日誌框架)

因為我是直接用回之前ElasticSearch的節點,而且也沒有清空數據,所以可以直接用之前註冊的賬號重新登錄

Exceptionless - .Net Core開源日誌框架(二)

也是成功的,ElasticSearch服務已經運行在後臺了。

自動啟動通過ElasticSearch提供的GUI可以將服務設置為自動啟動

<code>elasticsearch-service.bat manager
/<code>

將Startup Type選擇為Automatic,再點擊OK保存

Exceptionless - .Net Core開源日誌框架(二)

這樣,即使服務器重啟了,我們的ElasticSearch服務也會自動啟動

其實,有玩過Windows服務的朋友一定知道,上面的一些操作在Windows自帶的服務管理器也能完成

同時按下"WIN+R" 打開服務的命令運行窗口。在服務運行窗口中輸入services.msc

在列表中也可以找到ElasticSearch服務,雙擊打開屬性窗口,跟剛剛的GUI操作就是一樣的了

Exceptionless - .Net Core開源日誌框架(二)

再看Web.config

上次我只是改了Exceptionless的端口設置,其實這裡面還包含很多配置信息

<code>

/<code>

官方是建議大家安裝和配置Redis,這樣就可以同時運行多個實例,並且重啟不會丟失狀態,強烈建議在Linux上運行Redis 3.0+版本,RedisConnectionString就是Redis的連接串

ElasticSearchConnectionString是必須的,指向ElasticSearch服務,如果有多個節點,則使用,隔開

<code> 

 

 

 

 

/<code>

網站模式WebsiteMode主要是限制郵件發送,默認值是Dev,不發送郵件,所以我這裡設置為Production

郵件發送配置,記得跟上面的WebsiteMode一起配置

<code>




/<code>

我在案例中使用的是自己的qq郵箱。我在qq郵箱中已經開啟了SMTP服務,並且也通過一個控制檯應用程序測試可以發送郵件。但是在Exceptionless這裡一樣的設置就是不行,在Web中點擊發送郵件,log記錄錯誤如下:ERROR MailMessageJob Job run "MailMessageJob" failed: 由於意外的數據包格式,握手失敗。 System.IO.IOException: 由於意外的數據包格式,握手失敗。

清除Url我們現在使用的Url都會帶有#!,例如

<code>http://localhost:50001/#!/type/error/dashboard
/<code>

可以按照下面步驟清除字符#!

  • 首先保證你的IIS是否已經安裝了重寫模塊,可通過雙擊IIS中的模塊查看是否包含了RewriteModule
  • 更新Web.config文件釋放出在system.webServer中的rewrite節點刪除BaseURL值中的/#註釋了在system.webServer\modules中的標籤
  • 修改app.config.77fc9ddd679d37dc.js文件中USE_HTML5_MODE的值為true

進程外運行作業默認情況下,所有作業都在當前的Web進程中運行。如果發現事件處理開始變慢的時候,可以啟動並擴展多個作業實例。通過在進程外運行作業,可以確保所有作業是否正常運行。

  • 首先是要配置安裝Redis,這樣可以保證Exceptionless與作業之間能夠進行通信
  • 更新Web.config中的RunJobsInProcess值為false
  • 更新作業的配置,有兩種方法可選:使用環境變量進行配置Exceptionless。新增環境變量Exceptionless_{SETTING NAME} (例如: Exceptionless_BaseURL, Exceptionless_ElasticSearchConnectionString)。這是官方推薦的方法,因為它更簡單,而且當部署到azure時非常好用打開App_Data\jobs文件夾,然後按照在根目錄中Web.config的配置,再重新配置每個作業的xxx.exe.config。
  • 在每個作業文件夾中都有一個run.bat文件,雙擊它就會運行這個作業。當然,也可以將這些作業全部設置為Windows服務在後臺運行

更多設置除了上面提到的設置,Exceptionless還支持很多自定義配置,下面是全部的設置列表,大家可根據自己的需要進行定製列表按照這個格式進行排列:設置項 (數據類型,默認值)

<code>EnableSSL (bool)
BaseURL (string)
InternalProjectId (string, "54b56e480ef9605a88a13153")
WebsiteMode (WebsiteMode, "Dev")
AppScope (string, String.Empty)
TestEmailAddress (string)
AllowedOutboundAddresses (List, "exceptionless.io")
RunJobsInProcess (bool, true)
BotThrottleLimit (int, 25)
ApiThrottleLimit (int, Int32.MaxValue)
EventSubmissionDisabled (bool)
MaximumEventPostSize (long, 1000000)
MaximumRetentionDays (int, 180)
EnableDailySummary (bool)
MetricsServerName (string, "127.0.0.1")
MetricsServerPort (int, 8125)
EnableMetricsReporting (bool)
RedisConnectionString (string)
EnableRedis (bool)
DisableSnapshotJobs (bool)
DisableIndexConfiguration (bool)
ElasticSearchConnectionString (string)
ElasticSearchNumberOfShards (int, 1)
ElasticSearchNumberOfReplicas (int)
EnableElasticsearchTracing (bool)
LdapConnectionString (string)
EnableActiveDirectoryAuth (bool)
EnableSignalR (bool, true)
Version (string)
EnableIntercom (bool)
IntercomAppSecret (string)
EnableAccountCreation (bool, true)
MicrosoftAppId (string)
MicrosoftAppSecret (string)
FacebookAppId (string)
FacebookAppSecret (string)
GitHubAppId (string)
GitHubAppSecret (string)
GoogleAppId (string)
GoogleAppSecret (string)
GoogleGeocodingApiKey (string)
EnableBilling (bool)
StripeApiKey (string)
StorageFolder (string)
AzureStorageConnectionString (string)
EnableAzureStorage (bool)
BulkBatchSize (int, 1000)
SmtpHost (string)
SmtpPort (int, 587)
SmtpEnableSsl (bool, true)
SmtpUser (string)
SmtpPassword (string)
/<code>

更多日誌類型

Exceptionless除了支持記錄Exception,也可以記錄LogMessage、Broken Links 、Feature Usages

LogMessageLogMessage支持多種級別的日誌信息

  • Other
  • Trace
  • Debug
  • Info
  • Warn
  • Error
  • Fatal
  • Off

用法也很簡單,直接在你想要記錄日誌的地方直接加一句

<code>ExceptionlessClient.Default.CreateLog("日誌信息", LogLevel.Debug).AddTags("tag1", "tag2").Submit();
/<code> 

所以我們在應用的過程中,可以添加一個統一的接口

<code>public interface ILogger
{
    void Debug(string message, params string[] tags);
    void Error(string message, params string[] tags);
    void Fatal(string message, params string[] tags);
    void Info(string message, params string[] tags);
    void Off(string message, params string[] tags);
    void Other(string message, params string[] tags);
    void Trace(string message, params string[] tags);
    void Warn(string message, params string[] tags);
}
/<code>
<code>using Exceptionless;
using Exceptionless.Logging;
/<code>
<code>public class ExceptionlessLogger : ILogger
{
    public void Debug(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Debug).AddTags(tags).Submit();
    }

    public void Error(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Error).AddTags(tags).Submit();
    }

    public void Fatal(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Fatal).AddTags(tags).Submit();
    }

    public void Info(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Info).AddTags(tags).Submit();
    }

    public void Off(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Off).AddTags(tags).Submit();
    }

    public void Other(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Other).AddTags(tags).Submit();
    }

    public void Trace(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Trace).AddTags(tags).Submit();
    }

    public void Warn(string message, params string[] tags)
    {
        ExceptionlessClient.Default.CreateLog(message, LogLevel.Warn).AddTags(tags).Submit();
    }
}
/<code>

然後在Startup.cs的ConfigureServices方法注入ExceptionlessLogger

<code>public void ConfigureServices(IServiceCollection services)
{
    services.AddSingleton();
    services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_2);
}
/<code>

這樣就可以更方便地使用了

<code>public class ValuesController : ControllerBase
{
    public ILogger _logger;
    public ValuesController(ILogger logger)
    {
        _logger = logger;
    }
    
    // GET api/values/{id}
    [HttpGet("{id}")]
    public ActionResult Get(int id)
    {
        try
        {
            _logger.Info("Test msg", "tag1", "tag2");
            throw new Exception();
        }
        catch (Exception ex)
        {
            ex.ToExceptionless().AddTags("tag1", "tag2").Submit();
        }
        return $"value {id}";
    }
}
/<code>

Broken Links記錄404找不到請求的日誌

像我這裡沒有添加favicon.ico圖標,使用Chrome瀏覽器會自動請求這個資源,因此,Exceptionless就記錄了這樣的日誌

Exceptionless - .Net Core開源日誌框架(二)

也可以直接在Api服務中調用如下面語句添加這種類型的日誌

<code>ExceptionlessClient.Default.CreateNotFound("404 not found").SetType("404").SetSource($"api/values/{id}");
/<code>

Feature Usages類似的也可以添加Feature Usages日誌

<code>ExceptionlessClient.Default.CreateFeatureUsage("Feature 1").SetSource($"api/values/{id}").SetType("FeatureType").Submit();
/<code>

事件

上面所說的所有日誌類型,最終都會通過事件進行記錄,Exceptionless也支持我們直接記錄一個事件

例子如下:

<code>var dataDic = new Exceptionless.Models.DataDictionary();
dataDic.Add("key", "value");
ExceptionlessClient.Default.SubmitEvent(new Exceptionless.Models.Event
{
    Count = 1,
    Date = DateTime.Now,
    Data = dataDic,
    Geo = "geo",
    Message = "message",
    ReferenceId = "referencelId",
    Source = "source",
    Tags = new Exceptionless.Models.TagSet() { "tags" },
    Type = "type"
});
/<code>

Exceptionless同時也支持我們捕獲事件提交過程和事件提交後的事件,這樣我們就可以在過程中做一些操作,例如可以忽略404的請求,或者針對某些特殊日誌返回某些信息

為了代碼的整潔,可以將Exceptionless的配置單獨放到一個cs文件中

添加一個ExceptionlessBuilderExtensions類

<code>public static class ExceptionlessBuilderExtensions
{
    public static IApplicationBuilder UseExceptionless(this IApplicationBuilder app, IConfiguration configuration)
    {
        ExceptionlessClient.Default.Configuration.ApiKey = configuration["Exceptionless:ApiKey"];
        ExceptionlessClient.Default.Configuration.ServerUrl = configuration["Exceptionless:ServerUrl"];
        ExceptionlessClient.Default.SubmittingEvent += OnSubmittingEvent;
        app.UseExceptionless();

        return app;
    }

    private static void OnSubmittingEvent(object sender, EventSubmittingEventArgs e)
    {
        if (e.Event.IsNotFound())
        {
            e.Cancel = true;//取消事件提交
            return;
        }

        // 修改日誌信息
        if (e.Event.Source == "sourceA")
        {
            e.Event.AddTags("systemLog");
        }

        //TODO:
    }

    private static void OnSubmittedEvent(object sender, EventSubmittedEventArgs e)
    {
        // 做點什麼東西
        if (e.Event.Source == "sourceA")
        {
            //TODO:
        }
    }
}
/<code>

然後修改Startup.cs

<code>public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
    ……

    app.UseExceptionless(Configuration);

    ……
}
/<code> 

Exceptionless 日誌查詢

Exceptionless Web站點已經幫我們做好項目、時間、日誌類型的分類,大家可以很直觀地進行操作查詢。我這裡要關注的是Filter查詢

前面記錄日誌的時候,有添加了tag、Type等信息,這時候就可以使用Filter進行查詢了。語法:

<code>[FilterType]:[value1] {or} {[value2]}
/<code>

or是用於查詢多個該類型值的日誌時使用

例如:tag:tag1

Exceptionless - .Net Core開源日誌框架(二)

列幾個可能比較常用的

  • source:"my log source" or "my log source"
  • type:error
  • level:Error
  • ip:127.0.0.1

如果是要同時輸入多種類型的條件:

<code>[FilterType]:[value] {OR|AND} {[FilterType]:[value]}
/<code>

例如:tag:tag1 OR ip:127.0.0.1

更多的語法可以看官網說明https://github.com/exceptionless/Exceptionless/wiki/Filtering-Searching

總結

在這篇文章中,我基本就是順著Exceptionless Self Hosting的介紹做了一遍,不過有一些東西因為沒有實際環境,所以也沒有去做,然後我這個也只是一個Demo,暫時也沒有做相關的壓力測試,所以也不知道這貨真正在生產環境大量用起來的時候會有一些什麼表現,會不會踩到什麼坑


原文來源:博客園

原文地址:https://www.cnblogs.com/markjiang7m2/p/11100563.html


分享到:


相關文章: