From e092497af20b590fe51aae5086be6e4464fd4756 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:36:18 +0800 Subject: [PATCH 01/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E8=BF=90=E7=BB=B4?= =?UTF-8?q?=E6=96=87=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- build/CI.bat | 26 ++++++++++++++++++++++++++ build/version.props | 9 +++++++++ 2 files changed, 35 insertions(+) create mode 100644 build/CI.bat create mode 100644 build/version.props diff --git a/build/CI.bat b/build/CI.bat new file mode 100644 index 0000000..913483c --- /dev/null +++ b/build/CI.bat @@ -0,0 +1,26 @@ +set build-base-path=../exceptionless.webhooks +set outpust-base-path=../../build +set username=justmine + +for /f "delims=> tokens=2" %%i in ('findstr ".*" version.props')do set "Major=%%i"; +for /f "delims=> tokens=2" %%j in ('findstr ".*" version.props')do set "Minor=%%j"; +for /f "delims=> tokens=2" %%h in ('findstr ".*" version.props')do set "Patch=%%h"; + +set Major=%Major:~0,1% +set Minor=%Minor:~0,1% +set Patch=%Patch:~0,1% +set Version=%Major%.%Minor%.%Patch% + +set first=Web +set version=%Version% +set imagename=exceptionless.api.webhook +set imagefullname=%username%/%imagename%:%version% + +dotnet publish %build-base-path%/%first%/%first%.csproj -o %outpust-base-path%/%first% -c release +docker build -t %imagefullname% ./%first% +docker push %imagefullname% + +rd /s /q %first% + +pause +goto EOF \ No newline at end of file diff --git a/build/version.props b/build/version.props new file mode 100644 index 0000000..7d235ef --- /dev/null +++ b/build/version.props @@ -0,0 +1,9 @@ + + + 0 + 0 + 0 + + $(VersionMajor).$(VersionMinor).$(VersionPatch) + + \ No newline at end of file From baaa84bf0fb6bb1e497130a21f06a9b9ccbd8cfc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:36:51 +0800 Subject: [PATCH 02/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=AE=B9=E5=99=A8?= =?UTF-8?q?=E5=8C=96=E5=88=B0k8s=E7=9A=84=E7=9B=B8=E5=85=B3=E6=96=87?= =?UTF-8?q?=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- exceptionless.webhooks/Web/Dockerfile | 6 ++++ k8s/web.yml | 43 +++++++++++++++++++++++++++ 2 files changed, 49 insertions(+) create mode 100644 exceptionless.webhooks/Web/Dockerfile create mode 100644 k8s/web.yml diff --git a/exceptionless.webhooks/Web/Dockerfile b/exceptionless.webhooks/Web/Dockerfile new file mode 100644 index 0000000..a9c15d5 --- /dev/null +++ b/exceptionless.webhooks/Web/Dockerfile @@ -0,0 +1,6 @@ +FROM microsoft/dotnet:2.1-aspnetcore-runtime +RUN cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime +WORKDIR /app +COPY . . +EXPOSE 80 +ENTRYPOINT ["dotnet", "Web.dll"] \ No newline at end of file diff --git a/k8s/web.yml b/k8s/web.yml new file mode 100644 index 0000000..19dbef5 --- /dev/null +++ b/k8s/web.yml @@ -0,0 +1,43 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + namespace: geekbuying-light-addons + name: exceptionless-api-weebhook + labels: + app: exceptionless-api-weebhook +spec: + replicas: 1 + selector: + matchLabels: + app: exceptionless-api-weebhook + template: + metadata: + labels: + app: exceptionless-api-weebhook + spec: + containers: + - name: exceptionless-api-weebhook + image: "justmine/exceptionless.api.webhook:0.0.0" + imagePullPolicy: IfNotPresent + ports: + - name: http + containerPort: 80 + protocol: TCP + +--- +apiVersion: v1 +kind: Service +metadata: + namespace: geekbuying-light-addons + name: exceptionless-api-weebhook + labels: + app: exceptionless-api-weebhook +spec: + type: ClusterIP + ports: + - port: 80 + targetPort: http + protocol: TCP + name: http + selector: + app: exceptionless-api-weebhook \ No newline at end of file From 60ff3131111f319737de857f3ff1bf1fc6d2db67 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:37:19 +0800 Subject: [PATCH 03/41] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E5=B0=8F=E5=BF=83?= =?UTF-8?q?=E6=A8=A1=E6=9D=BF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Web/markdownTemplate.md | 21 +++++++++++-------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/exceptionless.webhooks/Web/markdownTemplate.md b/exceptionless.webhooks/Web/markdownTemplate.md index b39cc37..d923742 100644 --- a/exceptionless.webhooks/Web/markdownTemplate.md +++ b/exceptionless.webhooks/Web/markdownTemplate.md @@ -1,9 +1,12 @@ -# {OrganizationName}.{ProjectName} 有新的事件发生 -发生时间:{OccurrenceDate} -类型:{Type} -消息:{Message} -堆标题:{StackTitle} -第一次发生时间:{FirstOccurrence} -次数:{TotalOccurrences} -IP:{IpAddress} -[查看事件详情]({Url}) \ No newline at end of file +## [{Environment}]{OrganizationName}.{ProjectName} 有新事件发生: +- 类型:{Type} +- 发生时间:{OccurrenceDate} +- 第一次发生时间:{FirstOccurrence} +- 最后发生时间:{LastOccurrence} +- 发生总次数:{TotalOccurrences} +- 来源:{Source} +- 消息:{Message} +- 堆栈摘要:{StackTitle} +- 查看事件详情:{Url} +- 查看事件统计:{StackUrl} +- IP地址:{IpAddress} \ No newline at end of file From 57ebb85bb2c4a198a93ab1492a943b1b283b9707 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:37:37 +0800 Subject: [PATCH 04/41] =?UTF-8?q?=E8=B0=83=E6=95=B4=E6=96=87=E4=BB=B6?= =?UTF-8?q?=E4=BD=8D=E7=BD=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Utilities/StringUtility.cs} | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) rename exceptionless.webhooks/{Exceptionless.WebHook.DingTalk/Utilitys/StringUtilitys.cs => ExceptionLess.WebHook.DingTalk/Utilities/StringUtility.cs} (77%) diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Utilitys/StringUtilitys.cs b/exceptionless.webhooks/ExceptionLess.WebHook.DingTalk/Utilities/StringUtility.cs similarity index 77% rename from exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Utilitys/StringUtilitys.cs rename to exceptionless.webhooks/ExceptionLess.WebHook.DingTalk/Utilities/StringUtility.cs index 392080d..701e2a5 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Utilitys/StringUtilitys.cs +++ b/exceptionless.webhooks/ExceptionLess.WebHook.DingTalk/Utilities/StringUtility.cs @@ -1,6 +1,6 @@ -namespace Exceptionless.WebHook.DingTalk.Utilitys +namespace ExceptionLess.WebHook.DingTalk.Utilities { - public class StringUtilitys + public class StringUtility { public static string ToCamelCase(string str) { From b602a736f27bc58fc777a178440aaad9470a6a22 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:38:07 +0800 Subject: [PATCH 05/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E9=85=8D=E7=BD=AE?= =?UTF-8?q?=E6=96=87=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Web/appsettings.Development.json | 12 +++++++++ .../Web/appsettings.Production.json | 12 +++++++++ .../Web/appsettings.Staging.json | 12 +++++++++ .../Web/nlog.Production.config | 27 +++++++++++++++++++ .../Web/nlog.Staging.config | 27 +++++++++++++++++++ 5 files changed, 90 insertions(+) create mode 100644 exceptionless.webhooks/Web/appsettings.Development.json create mode 100644 exceptionless.webhooks/Web/appsettings.Production.json create mode 100644 exceptionless.webhooks/Web/appsettings.Staging.json create mode 100644 exceptionless.webhooks/Web/nlog.Production.config create mode 100644 exceptionless.webhooks/Web/nlog.Staging.config diff --git a/exceptionless.webhooks/Web/appsettings.Development.json b/exceptionless.webhooks/Web/appsettings.Development.json new file mode 100644 index 0000000..e5ac623 --- /dev/null +++ b/exceptionless.webhooks/Web/appsettings.Development.json @@ -0,0 +1,12 @@ +{ + "Logging": { + "IncludeScopes": true, + "LogLevel": { + "Default": "Debug", + "Microsoft": "Warning" + } + }, + "EnableModules": [ + "ExceptionLess.WebHook.DingTalk" + ] +} \ No newline at end of file diff --git a/exceptionless.webhooks/Web/appsettings.Production.json b/exceptionless.webhooks/Web/appsettings.Production.json new file mode 100644 index 0000000..9a530d5 --- /dev/null +++ b/exceptionless.webhooks/Web/appsettings.Production.json @@ -0,0 +1,12 @@ +{ + "Logging": { + "IncludeScopes": true, + "LogLevel": { + "Default": "Information", + "Microsoft": "Warning" + } + }, + "EnableModules": [ + "ExceptionLess.WebHook.DingTalk" + ] +} \ No newline at end of file diff --git a/exceptionless.webhooks/Web/appsettings.Staging.json b/exceptionless.webhooks/Web/appsettings.Staging.json new file mode 100644 index 0000000..e5ac623 --- /dev/null +++ b/exceptionless.webhooks/Web/appsettings.Staging.json @@ -0,0 +1,12 @@ +{ + "Logging": { + "IncludeScopes": true, + "LogLevel": { + "Default": "Debug", + "Microsoft": "Warning" + } + }, + "EnableModules": [ + "ExceptionLess.WebHook.DingTalk" + ] +} \ No newline at end of file diff --git a/exceptionless.webhooks/Web/nlog.Production.config b/exceptionless.webhooks/Web/nlog.Production.config new file mode 100644 index 0000000..87d5b9c --- /dev/null +++ b/exceptionless.webhooks/Web/nlog.Production.config @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/exceptionless.webhooks/Web/nlog.Staging.config b/exceptionless.webhooks/Web/nlog.Staging.config new file mode 100644 index 0000000..87d5b9c --- /dev/null +++ b/exceptionless.webhooks/Web/nlog.Staging.config @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file From 90edb724c4c615775452dce8d8955f71d0390548 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:38:26 +0800 Subject: [PATCH 06/41] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E5=80=BC=E5=90=8D?= =?UTF-8?q?=E7=A7=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- exceptionless.webhooks/Web/appsettings.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/exceptionless.webhooks/Web/appsettings.json b/exceptionless.webhooks/Web/appsettings.json index 4985bdf..e5ac623 100644 --- a/exceptionless.webhooks/Web/appsettings.json +++ b/exceptionless.webhooks/Web/appsettings.json @@ -2,11 +2,11 @@ "Logging": { "IncludeScopes": true, "LogLevel": { - "Default": "Information", + "Default": "Debug", "Microsoft": "Warning" } }, "EnableModules": [ - "Exceptionless.WebHook.DingTalk" + "ExceptionLess.WebHook.DingTalk" ] } \ No newline at end of file From 708c0c8908cb604130cd4f9089e8d6cf6d791e9a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:38:50 +0800 Subject: [PATCH 07/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E7=8E=AF=E5=A2=83?= =?UTF-8?q?=E5=92=8C=E6=9D=A5=E6=BA=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ExceptionlessEventModel.cs | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/ExceptionlessEventModel.cs b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/ExceptionlessEventModel.cs index c8109fa..26aaa6f 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/ExceptionlessEventModel.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/ExceptionlessEventModel.cs @@ -1,10 +1,12 @@ using Newtonsoft.Json; using System; -namespace Exceptionless.WebHook.Abstractions +namespace ExceptionLess.WebHook.Abstractions { - public class ExceptionlessEventModel + public class ExceptionLessEventModel { + public string Environment { get; set; } + public string Id { get; set; } public string Url { get; set; } @@ -12,11 +14,11 @@ public class ExceptionlessEventModel public DateTime OccurrenceDate { get; set; } public string Type { get; set; } + public string Source { get; set; } public string Message { get; set; } [JsonProperty("project_id")] public string ProjectId { get; set; } - [JsonProperty("project_Name")] public string ProjectName { get; set; } From 23bf9d13eff23d31f886eaad7c744a5f6807bcc3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:39:30 +0800 Subject: [PATCH 08/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E7=8E=AF=E5=A2=83?= =?UTF-8?q?=E4=BF=A1=E6=81=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DingTalkWebHookProvider.cs | 22 +++++++++++++------ 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/DingTalkWebHookProvider.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/DingTalkWebHookProvider.cs index 37ff175..7e05f42 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/DingTalkWebHookProvider.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/DingTalkWebHookProvider.cs @@ -1,37 +1,45 @@ -using Exceptionless.WebHook.Abstractions; -using Exceptionless.WebHook.DingTalk.Messages; -using Exceptionless.WebHook.DingTalk.Services; +using ExceptionLess.WebHook.Abstractions; +using ExceptionLess.WebHook.DingTalk.Messages; +using ExceptionLess.WebHook.DingTalk.Services; +using Microsoft.AspNetCore.Hosting; using System; using System.Collections.Generic; using System.Threading.Tasks; -namespace Exceptionless.WebHook.DingTalk +namespace ExceptionLess.WebHook.DingTalk { public class DingTalkWebHookProvider : IWebHookProvider { private readonly FileTemplateService _fileTemplateService; private readonly MessageService _messageService; + private readonly IHostingEnvironment _environment; - public DingTalkWebHookProvider(FileTemplateService fileTemplateService, MessageService messageService) + public DingTalkWebHookProvider( + FileTemplateService fileTemplateService, + MessageService messageService, + IHostingEnvironment environment) { _fileTemplateService = fileTemplateService; _messageService = messageService; + _environment = environment; } #region Implementation of IWebHookProvider public string Name { get; } = "DingTake"; - public async Task ProcessAsync(ExceptionlessEventModel model, IDictionary parameters) + public async Task ProcessAsync(ExceptionLessEventModel model, IDictionary parameters) { parameters.TryGetValue("accessToken", out var accessToken); + + model.Environment = _environment.EnvironmentName; var content = await _fileTemplateService.GetContent("markdownTemplate.md", model); await _messageService.SendAsync( new Uri($"https://oapi.dingtalk.com/robot/send?access_token={accessToken}"), new DingTalkRequestMessage { - Data = new MarkdownDingTalkMessage("Exceptionless 有新的事件", content) + Data = new MarkdownDingTalkMessage($"[{_environment.EnvironmentName}]ExceptionLess有新事件", content) }); } From 9f3ed4aa2d8c7313d47f694e47d9bb7457cdcbf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:39:49 +0800 Subject: [PATCH 09/41] =?UTF-8?q?=E4=BC=98=E5=8C=96httpclient=E4=BD=BF?= =?UTF-8?q?=E7=94=A8=E6=96=B9=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Services/MessageService.cs | 35 +++++++++---------- 1 file changed, 17 insertions(+), 18 deletions(-) diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Services/MessageService.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Services/MessageService.cs index 4ad96bb..4f2a171 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Services/MessageService.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Services/MessageService.cs @@ -1,5 +1,5 @@ -using Exceptionless.WebHook.DingTalk.Messages; -using Exceptionless.WebHook.DingTalk.Utilitys; +using ExceptionLess.WebHook.DingTalk.Messages; +using ExceptionLess.WebHook.DingTalk.Utilities; using Microsoft.Extensions.Logging; using Newtonsoft.Json; using Rabbit.Extensions.DependencyInjection; @@ -9,15 +9,17 @@ using System.Text; using System.Threading.Tasks; -namespace Exceptionless.WebHook.DingTalk.Services +namespace ExceptionLess.WebHook.DingTalk.Services { public class MessageService : ISingletonDependency { private readonly ILogger _logger; + private readonly IHttpClientFactory _httpClientFactory; - public MessageService(ILogger logger) + public MessageService(ILogger logger, IHttpClientFactory httpClientFactory) { _logger = logger; + _httpClientFactory = httpClientFactory; } public async Task SendAsync(Uri url, DingTalkRequestMessage message) @@ -25,7 +27,7 @@ public async Task SendAsync(Uri url, DingTalkRequestMessage message) if (_logger.IsEnabled(LogLevel.Debug)) _logger.LogDebug($"准备向 {url} 发送数据"); - var type = StringUtilitys.ToCamelCase(message.Type.ToString()); + var type = StringUtility.ToCamelCase(message.Type.ToString()); var data = new Dictionary { {"msgtype", type}, @@ -35,23 +37,20 @@ public async Task SendAsync(Uri url, DingTalkRequestMessage message) var json = JsonConvert.SerializeObject(data); if (_logger.IsEnabled(LogLevel.Debug)) - _logger.LogDebug($"send dingtalk json:{json}"); + _logger.LogDebug($"send dingTalk json:{json}"); string responseContent = null; try { - using (var client = new HttpClient()) - { - var result = await client.PostAsync(url, new StringContent(json, Encoding.UTF8, "application/json")); - responseContent = await result.Content.ReadAsStringAsync(); - - if (_logger.IsEnabled(LogLevel.Debug)) - _logger.LogDebug(responseContent); - - var response = JsonConvert.DeserializeObject(responseContent); - if (response.ErrorCode > 0) - _logger.LogError($"钉钉返回错误消息:{responseContent}"); - } + var result = await _httpClientFactory.CreateClient().PostAsync(url, new StringContent(json, Encoding.UTF8, "application/json")); + responseContent = await result.Content.ReadAsStringAsync(); + + if (_logger.IsEnabled(LogLevel.Debug)) + _logger.LogDebug(responseContent); + + var response = JsonConvert.DeserializeObject(responseContent); + if (response.ErrorCode > 0) + _logger.LogError($"钉钉返回错误消息:{responseContent}"); } catch (Exception e) { From 52b1c57e5bf14ee5a98d964f5b587a7759b20f12 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:40:26 +0800 Subject: [PATCH 10/41] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E9=85=8D=E7=BD=AE?= =?UTF-8?q?=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- exceptionless.webhooks/Web/Program.cs | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/exceptionless.webhooks/Web/Program.cs b/exceptionless.webhooks/Web/Program.cs index 7ceff57..7bd1c63 100644 --- a/exceptionless.webhooks/Web/Program.cs +++ b/exceptionless.webhooks/Web/Program.cs @@ -1,6 +1,7 @@ using Microsoft.AspNetCore; using Microsoft.AspNetCore.Hosting; using Microsoft.Extensions.Logging; +using NLog.Extensions.Logging; using NLog.Web; using System; using System.Collections.Generic; @@ -19,26 +20,29 @@ public static IWebHost BuildWebHost(string[] args) => WebHost.CreateDefaultBuilder(args) .ConfigureLogging((ctx, builder) => { + var env = ctx.HostingEnvironment; IEnumerable GetNlogConfigFiles() { - yield return $"nlog.{ctx.HostingEnvironment.EnvironmentName}.config"; + yield return $"nlog.{env.EnvironmentName}.config"; yield return "nlog.config"; } string GetNlogConfigFile() { return GetNlogConfigFiles().FirstOrDefault(f => - ctx.HostingEnvironment.ContentRootFileProvider.GetFileInfo(f).Exists); + env.ContentRootFileProvider.GetFileInfo(f).Exists); } var configFile = GetNlogConfigFile(); if (configFile == null) throw new Exception("找不到nlog的配置文件"); + env.ConfigureNLog(configFile); + builder .AddConfiguration(ctx.Configuration) .AddConsole() - .ConfigureNLog(configFile); + .AddNLog(); }) .UseStartup() .UseNLog() From 0d0849f9718eabe9123230e713099d80b471fe76 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:40:59 +0800 Subject: [PATCH 11/41] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=BA=8F=E5=88=97?= =?UTF-8?q?=E5=8C=96=E6=97=B6=E9=97=B4=E5=8C=BA=E5=9F=9F=E6=80=A7=E8=AE=BE?= =?UTF-8?q?=E7=BD=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- exceptionless.webhooks/Web/Startup.cs | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/exceptionless.webhooks/Web/Startup.cs b/exceptionless.webhooks/Web/Startup.cs index efa9372..1766068 100644 --- a/exceptionless.webhooks/Web/Startup.cs +++ b/exceptionless.webhooks/Web/Startup.cs @@ -2,8 +2,8 @@ using Microsoft.AspNetCore.Hosting; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Logging; -using NLog.Extensions.Logging; +using Newtonsoft.Json; +using Newtonsoft.Json.Serialization; using Rabbit.Extensions.DependencyInjection; using System; using System.Linq; @@ -27,34 +27,39 @@ public void ConfigureServices(IServiceCollection services) { var appSettings = Configuration.Get(); - var enableModules = new[] { "Exceptionless.WebHook.Abstractions" }.Concat(appSettings.EnableModules) + var enableModules = new[] { "ExceptionLess.WebHook.Abstractions" }.Concat(appSettings.EnableModules) .ToDictionary(name => name, name => Assembly.Load(new AssemblyName(name))); foreach (var item in enableModules.Where(i => i.Value == null)) Console.WriteLine($"无法加载模块:{item.Key}"); var assemblies = enableModules.Values.ToArray(); + services .AddLogging() .AddMemoryCache() + .AddHttpClient() .AddInterfaceDependency(assemblies) .AddMvc(); + + JsonConvert.DefaultSettings = () => new JsonSerializerSettings + { + Formatting = Formatting.Indented, + ContractResolver = new CamelCasePropertyNamesContractResolver(), + DateTimeZoneHandling = DateTimeZoneHandling.Local + }; } // This method gets called by the runtime. Use this method to configure the HTTP request pipeline. - public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory) + public void Configure(IApplicationBuilder app, IHostingEnvironment env) { - loggerFactory - .AddNLog(); - app.UseStatusCodePages(); if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } - app - .UseMiddleware(); + app.UseMiddleware(); } } } \ No newline at end of file From 60197f99379f2408c3410788a9e09ad41f710a01 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E4=BA=8C=E6=AF=9B?= Date: Fri, 16 Nov 2018 16:41:52 +0800 Subject: [PATCH 12/41] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E5=91=BD=E5=90=8D?= =?UTF-8?q?=E7=A9=BA=E9=97=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Exceptionless.WebHook.Abstractions.csproj | 12 +++++------ .../FileTemplateService.cs | 18 ++++++++--------- .../IWebHookProvider.cs | 4 ++-- .../Exceptionless.WebHook.DingTalk.csproj | 15 +++++++++++--- .../Messages/DingTalkRequestMessage.cs | 2 +- .../Messages/DingTalkResponseMessage.cs | 2 +- .../Messages/MessageType.cs | 2 +- .../Messages/Messages.cs | 2 +- .../ExceptionlessWebhookMiddleware.cs | 15 +++++++------- exceptionless.webhooks/Web/Web.csproj | 20 +++++++++++-------- .../exceptionless.webhooks.sln | 15 +++++++++++--- 11 files changed, 65 insertions(+), 42 deletions(-) diff --git a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/Exceptionless.WebHook.Abstractions.csproj b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/Exceptionless.WebHook.Abstractions.csproj index 77e1e74..8978979 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/Exceptionless.WebHook.Abstractions.csproj +++ b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/Exceptionless.WebHook.Abstractions.csproj @@ -5,12 +5,12 @@ - - - - - - + + + + + + diff --git a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/FileTemplateService.cs b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/FileTemplateService.cs index fbadb3e..42e2c5c 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/FileTemplateService.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/FileTemplateService.cs @@ -8,14 +8,14 @@ using System.Text; using System.Threading.Tasks; -namespace Exceptionless.WebHook.Abstractions +namespace ExceptionLess.WebHook.Abstractions { public class FileTemplateService : ISingletonDependency, IDisposable { #region Field private readonly IMemoryCache _memoryCache; - private readonly PhysicalFileProvider _physicalFileProvider; + private readonly PhysicalFileProvider _fileProvider; #endregion Field @@ -24,7 +24,7 @@ public class FileTemplateService : ISingletonDependency, IDisposable public FileTemplateService(IMemoryCache memoryCache) { _memoryCache = memoryCache; - _physicalFileProvider = new PhysicalFileProvider(AppContext.BaseDirectory); + _fileProvider = new PhysicalFileProvider(AppContext.BaseDirectory); } #endregion Constructor @@ -40,17 +40,17 @@ public async Task GetContent(string templateFile, object model) var properties = model.GetType().GetProperties(); var builder = new StringBuilder(template); - var propertys = new Dictionary(); + var propCache = new Dictionary(); string GetPropertyValue(PropertyInfo property) { - if (propertys.TryGetValue(property.Name, out var value)) + if (propCache.TryGetValue(property.Name, out var value)) { return value; } value = property.GetValue(model)?.ToString(); - propertys[property.Name] = value; + propCache[property.Name] = value; return value; } @@ -72,8 +72,8 @@ private async Task GetTemplate(string templateFile) { return await _memoryCache.GetOrCreateAsync(templateFile, async entry => { - entry.AddExpirationToken(_physicalFileProvider.Watch(templateFile)); - var fileInfo = _physicalFileProvider.GetFileInfo(templateFile); + entry.AddExpirationToken(_fileProvider.Watch(templateFile)); + var fileInfo = _fileProvider.GetFileInfo(templateFile); if (!fileInfo.Exists) return string.Empty; @@ -92,7 +92,7 @@ private async Task GetTemplate(string templateFile) public void Dispose() { _memoryCache?.Dispose(); - _physicalFileProvider?.Dispose(); + _fileProvider?.Dispose(); } #endregion IDisposable diff --git a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/IWebHookProvider.cs b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/IWebHookProvider.cs index ac92ebb..6eca826 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/IWebHookProvider.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.Abstractions/IWebHookProvider.cs @@ -2,12 +2,12 @@ using System.Collections.Generic; using System.Threading.Tasks; -namespace Exceptionless.WebHook.Abstractions +namespace ExceptionLess.WebHook.Abstractions { public interface IWebHookProvider : ISingletonDependency { string Name { get; } - Task ProcessAsync(ExceptionlessEventModel model, IDictionary parameters); + Task ProcessAsync(ExceptionLessEventModel model, IDictionary parameters); } } \ No newline at end of file diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Exceptionless.WebHook.DingTalk.csproj b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Exceptionless.WebHook.DingTalk.csproj index 7e0d93d..ee9cc48 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Exceptionless.WebHook.DingTalk.csproj +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Exceptionless.WebHook.DingTalk.csproj @@ -5,12 +5,21 @@ - - + + - + + + + + + C:\Program Files\dotnet\sdk\NuGetFallbackFolder\microsoft.aspnetcore.hosting.abstractions\2.1.1\lib\netstandard2.0\Microsoft.AspNetCore.Hosting.Abstractions.dll + + + C:\Users\justmine\.nuget\packages\microsoft.extensions.http\2.1.1\lib\netstandard2.0\Microsoft.Extensions.Http.dll + \ No newline at end of file diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkRequestMessage.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkRequestMessage.cs index 642fbc7..4093f57 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkRequestMessage.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkRequestMessage.cs @@ -1,4 +1,4 @@ -namespace Exceptionless.WebHook.DingTalk.Messages +namespace ExceptionLess.WebHook.DingTalk.Messages { public class DingTalkRequestMessage { diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkResponseMessage.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkResponseMessage.cs index f7d6db1..4f6f3ab 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkResponseMessage.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/DingTalkResponseMessage.cs @@ -1,6 +1,6 @@ using Newtonsoft.Json; -namespace Exceptionless.WebHook.DingTalk.Messages +namespace ExceptionLess.WebHook.DingTalk.Messages { public class DingTalkResponseMessage { diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/MessageType.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/MessageType.cs index afc793b..b96c5bf 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/MessageType.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/MessageType.cs @@ -1,4 +1,4 @@ -namespace Exceptionless.WebHook.DingTalk.Messages +namespace ExceptionLess.WebHook.DingTalk.Messages { public enum MessageType { diff --git a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/Messages.cs b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/Messages.cs index b44debc..2324fa3 100644 --- a/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/Messages.cs +++ b/exceptionless.webhooks/Exceptionless.WebHook.DingTalk/Messages/Messages.cs @@ -1,6 +1,6 @@ using Newtonsoft.Json; -namespace Exceptionless.WebHook.DingTalk.Messages +namespace ExceptionLess.WebHook.DingTalk.Messages { public abstract class DingTalkMessageBase { diff --git a/exceptionless.webhooks/Web/Middleware/ExceptionlessWebhookMiddleware.cs b/exceptionless.webhooks/Web/Middleware/ExceptionlessWebhookMiddleware.cs index 68890b0..e6dd023 100644 --- a/exceptionless.webhooks/Web/Middleware/ExceptionlessWebhookMiddleware.cs +++ b/exceptionless.webhooks/Web/Middleware/ExceptionlessWebhookMiddleware.cs @@ -1,4 +1,5 @@ -using Exceptionless.WebHook.Abstractions; +using ExceptionLess.WebHook.Abstractions; +using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Http; using Microsoft.Extensions.Logging; using Newtonsoft.Json; @@ -10,23 +11,24 @@ namespace Web.Middleware { - public class ExceptionlessWebhookMiddleware + public class ExceptionLessWebhookMiddleware { #region Field private readonly RequestDelegate _next; private readonly IEnumerable _webHookProviders; - private readonly ILogger _logger; + private readonly ILogger _logger; #endregion Field #region Constructor - public ExceptionlessWebhookMiddleware(RequestDelegate next, IEnumerable webHookProviders, ILogger logger) + public ExceptionLessWebhookMiddleware(RequestDelegate next, IEnumerable webHookProviders, ILogger logger) { _next = next; _webHookProviders = webHookProviders; _logger = logger; + if (_logger.IsEnabled(LogLevel.Debug)) _logger.LogDebug($"全部处理程序数量:{_webHookProviders.Count()}"); } @@ -54,9 +56,8 @@ public async Task Invoke(HttpContext context) if (_logger.IsEnabled(LogLevel.Debug)) _logger.LogDebug($"接收到 Webhook 请求:{content}"); - - var model = JsonConvert.DeserializeObject(content); - + + var model = JsonConvert.DeserializeObject(content); var providers = GetProviders(request.Query); var parameters = new Dictionary(request.Query.ToDictionary(i => i.Key, i => i.Value.ToString()), StringComparer.OrdinalIgnoreCase); diff --git a/exceptionless.webhooks/Web/Web.csproj b/exceptionless.webhooks/Web/Web.csproj index ccdaf39..289bcdb 100644 --- a/exceptionless.webhooks/Web/Web.csproj +++ b/exceptionless.webhooks/Web/Web.csproj @@ -1,21 +1,25 @@  - netcoreapp2.0 + netcoreapp2.1 - - - - - + + + + + + - - + + + + PreserveNewest + PreserveNewest diff --git a/exceptionless.webhooks/exceptionless.webhooks.sln b/exceptionless.webhooks/exceptionless.webhooks.sln index 22b19cc..50b01a4 100644 --- a/exceptionless.webhooks/exceptionless.webhooks.sln +++ b/exceptionless.webhooks/exceptionless.webhooks.sln @@ -3,11 +3,17 @@ Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio 15 VisualStudioVersion = 15.0.26430.13 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Web", "Web\Web.csproj", "{0A3A9747-0A0D-47A6-AB91-6DC77670C710}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Web", "Web\Web.csproj", "{0A3A9747-0A0D-47A6-AB91-6DC77670C710}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Exceptionless.WebHook.Abstractions", "Exceptionless.WebHook.Abstractions\Exceptionless.WebHook.Abstractions.csproj", "{37702FD2-77F9-482F-A21E-B88A33AA2D40}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExceptionLess.WebHook.Abstractions", "Exceptionless.WebHook.Abstractions\ExceptionLess.WebHook.Abstractions.csproj", "{37702FD2-77F9-482F-A21E-B88A33AA2D40}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Exceptionless.WebHook.DingTalk", "Exceptionless.WebHook.DingTalk\Exceptionless.WebHook.DingTalk.csproj", "{DDA628F0-EB63-4C34-A87D-C1296F5970DC}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExceptionLess.WebHook.DingTalk", "ExceptionLess.WebHook.DingTalk\ExceptionLess.WebHook.DingTalk.csproj", "{DDA628F0-EB63-4C34-A87D-C1296F5970DC}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{7024BD80-0B3D-4586-8B3E-452BDC0ED615}" + ProjectSection(SolutionItems) = preProject + ..\build\CI.bat = ..\build\CI.bat + ..\build\version.props = ..\build\version.props + EndProjectSection EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution @@ -31,4 +37,7 @@ Global GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {80D25D1F-798A-4CFF-9780-450723F9B0A4} + EndGlobalSection EndGlobal From 73e42225f81b5befc9c2b455354ce1b63bcb6bb9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:12:20 +0800 Subject: [PATCH 13/41] Update README.md --- README.md | 64 +++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 62 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 2f2e805..ff25856 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,64 @@ # exceptionless-webhooks 一个 Exceptionless 相关 WebHooks 项目。 -## 目标 -DingTalk(钉钉) + +# 流程 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 + +# 部署 +## docker +docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 + +## kubernetes(推荐) +```shell +apiVersion: apps/v1 +kind: Deployment +metadata: + namespace: geekbuying-light-addons + name: exceptionless-api-weebhook + labels: + app: exceptionless-api-weebhook +spec: + replicas: 1 + selector: + matchLabels: + app: exceptionless-api-weebhook + template: + metadata: + labels: + app: exceptionless-api-weebhook + spec: + containers: + - name: exceptionless-api-weebhook + image: "justmine/exceptionless.api.webhook:0.0.0" + imagePullPolicy: IfNotPresent + ports: + - name: http + containerPort: 80 + protocol: TCP + +--- +apiVersion: v1 +kind: Service +metadata: + namespace: geekbuying-light-addons + name: exceptionless-api-weebhook + labels: + app: exceptionless-api-weebhook +spec: + type: ClusterIP + ports: + - port: 80 + targetPort: http + protocol: TCP + name: http + selector: + app: exceptionless-api-weebhook +``` + +# changes + +1. 添加容器化部署脚本,支持docker、kubernetes。 +2. 扩展事件模型,添加环境、来源等信息。 +3. 升级项目为netcoreapp2.1。 +4. 优化httpclient使用方式。 +5. 添加事件时间本地化设置。 From 01d8143518daf09ec7f425918ffba3c86711fe2e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:12:57 +0800 Subject: [PATCH 14/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index ff25856..f61a65e 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,7 @@ 一个 Exceptionless 相关 WebHooks 项目。 # 流程 -当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知晓线上程序运行情况。 # 部署 ## docker From a6de3f76ee234a2fe6854b2ce01d796b932f2fa2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:13:21 +0800 Subject: [PATCH 15/41] Update README.md --- README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/README.md b/README.md index f61a65e..ea8743b 100644 --- a/README.md +++ b/README.md @@ -35,7 +35,6 @@ spec: - name: http containerPort: 80 protocol: TCP - --- apiVersion: v1 kind: Service From ecbca22f617dfb647723723cf67e777e0dd339db Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:26:38 +0800 Subject: [PATCH 16/41] Update README.md --- README.md | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index ea8743b..3c3bc7a 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,8 @@ # exceptionless-webhooks 一个 Exceptionless 相关 WebHooks 项目。 -# 流程 -当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知晓线上程序运行情况。 +# 说明 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 # 部署 ## docker @@ -35,6 +35,7 @@ spec: - name: http containerPort: 80 protocol: TCP + --- apiVersion: v1 kind: Service @@ -54,6 +55,20 @@ spec: app: exceptionless-api-weebhook ``` +# 配置 + +请先部署好webhook钩子。 + +## Exceptionless + +Admin => Projects => Integrations => Add Web Hook: + + + +# 效果图 + + + # changes 1. 添加容器化部署脚本,支持docker、kubernetes。 From a0127c1b79580b429558fd3ac5b9063cdd4d7cde Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:33:31 +0800 Subject: [PATCH 17/41] Add files via upload --- config.png | Bin 0 -> 25600 bytes result.png | Bin 0 -> 42903 bytes 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 config.png create mode 100644 result.png diff --git a/config.png b/config.png new file mode 100644 index 0000000000000000000000000000000000000000..05807b4a76f9934e39e26b3ca2211d8c7bf15ebe GIT binary patch literal 25600 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 d7)VZCL;)! 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 OM@~vfvKaaF^}hjN^9bhv literal 0 HcmV?d00001 From a65a2dcb415ab246085a935f082d82a00e1ad148 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:34:55 +0800 Subject: [PATCH 18/41] Update README.md --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 3c3bc7a..bd0809a 100644 --- a/README.md +++ b/README.md @@ -63,11 +63,11 @@ spec: Admin => Projects => Integrations => Add Web Hook: - +![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/config.png) # 效果图 - +![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/result.png) # changes From d1a268019596595e4511d170af9fe0e2500e2b35 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:35:52 +0800 Subject: [PATCH 19/41] Update README.md --- README.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/README.md b/README.md index bd0809a..8916b8a 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,6 @@ -# exceptionless-webhooks 一个 Exceptionless 相关 WebHooks 项目。 -# 说明 +# 目的 当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 # 部署 From 2502d256addd8ea869c8f4b0adf677e102123283 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:37:33 +0800 Subject: [PATCH 20/41] Update README.md --- README.md | 45 +-------------------------------------------- 1 file changed, 1 insertion(+), 44 deletions(-) diff --git a/README.md b/README.md index 8916b8a..6ffc7a4 100644 --- a/README.md +++ b/README.md @@ -8,51 +8,8 @@ docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 ## kubernetes(推荐) -```shell -apiVersion: apps/v1 -kind: Deployment -metadata: - namespace: geekbuying-light-addons - name: exceptionless-api-weebhook - labels: - app: exceptionless-api-weebhook -spec: - replicas: 1 - selector: - matchLabels: - app: exceptionless-api-weebhook - template: - metadata: - labels: - app: exceptionless-api-weebhook - spec: - containers: - - name: exceptionless-api-weebhook - image: "justmine/exceptionless.api.webhook:0.0.0" - imagePullPolicy: IfNotPresent - ports: - - name: http - containerPort: 80 - protocol: TCP ---- -apiVersion: v1 -kind: Service -metadata: - namespace: geekbuying-light-addons - name: exceptionless-api-weebhook - labels: - app: exceptionless-api-weebhook -spec: - type: ClusterIP - ports: - - port: 80 - targetPort: http - protocol: TCP - name: http - selector: - app: exceptionless-api-weebhook -``` +![deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) # 配置 From 5fb311d6368f832bdcb726fee5763794eaba6eed Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:38:01 +0800 Subject: [PATCH 21/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 6ffc7a4..0306668 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,7 @@ docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 ## kubernetes(推荐) -![deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) +[deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) # 配置 From 0f13d37ccf556f53235293d45d12a594f4441fdc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:38:23 +0800 Subject: [PATCH 22/41] Update README.md --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index 0306668..fb7fc61 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,10 @@ # 部署 ## docker + +``` shell docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 +``` ## kubernetes(推荐) From 1e7850ef5785caae532fcffafb9be6ec6fe2e592 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:39:14 +0800 Subject: [PATCH 23/41] Update README.md --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index fb7fc61..643abcc 100644 --- a/README.md +++ b/README.md @@ -3,6 +3,10 @@ # 目的 当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 +# 效果图 + +![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/result.png) + # 部署 ## docker @@ -24,10 +28,6 @@ Admin => Projects => Integrations => Add Web Hook: ![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/config.png) -# 效果图 - -![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/result.png) - # changes 1. 添加容器化部署脚本,支持docker、kubernetes。 From 1d935e707fb8fe8e65b81e5ea4371024a4da0bf0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:40:39 +0800 Subject: [PATCH 24/41] Update README.md --- README.md | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 643abcc..fae3e58 100644 --- a/README.md +++ b/README.md @@ -7,22 +7,23 @@ ![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/result.png) -# 部署 -## docker +# 步骤 +## 1 部署 +### docker ``` shell docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 ``` -## kubernetes(推荐) +### kubernetes(推荐) [deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) -# 配置 +## 2 配置 请先部署好webhook钩子。 -## Exceptionless +### Exceptionless Admin => Projects => Integrations => Add Web Hook: From 48b50d98552a9e8e1e53ab3c119c0c9889b5f836 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:43:22 +0800 Subject: [PATCH 25/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index fae3e58..8c5e066 100644 --- a/README.md +++ b/README.md @@ -35,4 +35,4 @@ Admin => Projects => Integrations => Add Web Hook: 2. 扩展事件模型,添加环境、来源等信息。 3. 升级项目为netcoreapp2.1。 4. 优化httpclient使用方式。 -5. 添加事件时间本地化设置。 +5. 添加事件时间本地化设置。 From 8be07be3b3a7d7bea8dac8066b624b6821d167a7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:44:15 +0800 Subject: [PATCH 26/41] Update README.md --- README.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 8c5e066..58e704d 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,8 @@ ![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/result.png) # 步骤 -## 1 部署 +## 1、部署 +选择一种部署方式。 ### docker ``` shell @@ -19,7 +20,7 @@ docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 [deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) -## 2 配置 +## 2、配置 请先部署好webhook钩子。 @@ -35,4 +36,4 @@ Admin => Projects => Integrations => Add Web Hook: 2. 扩展事件模型,添加环境、来源等信息。 3. 升级项目为netcoreapp2.1。 4. 优化httpclient使用方式。 -5. 添加事件时间本地化设置。 +5. 添加事件时间本地化设置。 From a8fd70945f5aaf9bf21670ef7189871dd72227b1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:49:11 +0800 Subject: [PATCH 27/41] Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 58e704d..add1440 100644 --- a/README.md +++ b/README.md @@ -30,6 +30,8 @@ Admin => Projects => Integrations => Add Web Hook: ![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/config.png) +>注意:如果你的项目Webhook配置选项没有Error、LogEroor类型,说明Exceptionless还没有合并我的PR,请先拉取我的项目:[后端](https://github.com/justmine66/Exceptionless)、[前端](https://github.com/justmine66/Exceptionless.UI),前后端都需要拉取最新项目代码。 + # changes 1. 添加容器化部署脚本,支持docker、kubernetes。 From f107411c7179906760a6dc6d41b9bc23ce133030 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:49:35 +0800 Subject: [PATCH 28/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index add1440..485663a 100644 --- a/README.md +++ b/README.md @@ -30,7 +30,7 @@ Admin => Projects => Integrations => Add Web Hook: ![Image text](https://github.com/justmine66/exceptionless-webhooks/blob/master/config.png) ->注意:如果你的项目Webhook配置选项没有Error、LogEroor类型,说明Exceptionless还没有合并我的PR,请先拉取我的项目:[后端](https://github.com/justmine66/Exceptionless)、[前端](https://github.com/justmine66/Exceptionless.UI),前后端都需要拉取最新项目代码。 +>注意:如果你的项目Webhook配置选项没有Error、LogEroor类型,说明Exceptionless团队还没有合并我的PR,请先拉取我的项目:[后端](https://github.com/justmine66/Exceptionless)、[前端](https://github.com/justmine66/Exceptionless.UI),前后端都需要拉取最新项目代码。 # changes From affbe0b9ad2490700e7214c007086eb366be25e6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:51:20 +0800 Subject: [PATCH 29/41] Update README.md --- README.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/README.md b/README.md index 485663a..e3ba135 100644 --- a/README.md +++ b/README.md @@ -20,6 +20,11 @@ docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 [deployment.yml](https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml) +``` shell +kubectl apply -f https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml; +或 +kubectl -n [指定的命名空间] apply -f https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml; +``` ## 2、配置 请先部署好webhook钩子。 From 547ca534cb189c3b6c4090e58756a9ed9f4abe1c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:55:10 +0800 Subject: [PATCH 30/41] Update README.md --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index e3ba135..a646b47 100644 --- a/README.md +++ b/README.md @@ -44,3 +44,6 @@ Admin => Projects => Integrations => Add Web Hook: 3. 升级项目为netcoreapp2.1。 4. 优化httpclient使用方式。 5. 添加事件时间本地化设置。 + +# 如有疑惑,欢迎QQ。 +3538307147 From f5f015811cbb85ae6b89e61b8b1b15a1e1e2266d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:55:29 +0800 Subject: [PATCH 31/41] Update README.md From e6c16e504564d047de22b16fbee372a33b4d2f44 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:59:10 +0800 Subject: [PATCH 32/41] Update README.md --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index a646b47..db895e3 100644 --- a/README.md +++ b/README.md @@ -9,12 +9,12 @@ # 步骤 ## 1、部署 -选择一种部署方式。 -### docker + 选择一种部署方式。 + ### docker -``` shell -docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 -``` + ``` shell + docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 + ``` ### kubernetes(推荐) From 63ddc4ae6563f04a0faa246eac0bfc09c86a7011 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 17:59:39 +0800 Subject: [PATCH 33/41] Update README.md --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index db895e3..a646b47 100644 --- a/README.md +++ b/README.md @@ -9,12 +9,12 @@ # 步骤 ## 1、部署 - 选择一种部署方式。 - ### docker +选择一种部署方式。 +### docker - ``` shell - docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 - ``` +``` shell +docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 +``` ### kubernetes(推荐) From c175961f2d7ca6246c53d0fbb40b26e1da560b21 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 18:00:03 +0800 Subject: [PATCH 34/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index a646b47..735df1e 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,7 @@ # 步骤 ## 1、部署 -选择一种部署方式。 +请选择一种部署方式。 ### docker ``` shell From 6c293814bdfcea57bac9c63f0ace7742a94ee9b3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 18:01:39 +0800 Subject: [PATCH 35/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 735df1e..9593a92 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ 一个 Exceptionless 相关 WebHooks 项目。 # 目的 -当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知道线上程序运行情况。 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知晓线上程序运行情况。 # 效果图 From 9355033d2cbe0014023fa08c68a5f7bbcbc93fdd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 18:02:32 +0800 Subject: [PATCH 36/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 9593a92..d23dd1c 100644 --- a/README.md +++ b/README.md @@ -43,7 +43,7 @@ Admin => Projects => Integrations => Add Web Hook: 2. 扩展事件模型,添加环境、来源等信息。 3. 升级项目为netcoreapp2.1。 4. 优化httpclient使用方式。 -5. 添加事件时间本地化设置。 +5. 本地化事件模型时间。 # 如有疑惑,欢迎QQ。 3538307147 From 5c9cee858489efecc09bf43d08873b9a81f1a93f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 05:44:57 -0800 Subject: [PATCH 37/41] Update web.yml --- k8s/web.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/k8s/web.yml b/k8s/web.yml index 19dbef5..cbd4414 100644 --- a/k8s/web.yml +++ b/k8s/web.yml @@ -1,7 +1,7 @@ apiVersion: apps/v1 kind: Deployment metadata: - namespace: geekbuying-light-addons + namespace: default name: exceptionless-api-weebhook labels: app: exceptionless-api-weebhook @@ -40,4 +40,4 @@ spec: protocol: TCP name: http selector: - app: exceptionless-api-weebhook \ No newline at end of file + app: exceptionless-api-weebhook From 414aa4805184c8fb8b6c64d5f04bddce7b8c61c2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Fri, 16 Nov 2018 05:45:54 -0800 Subject: [PATCH 38/41] Update README.md --- README.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/README.md b/README.md index d23dd1c..f920434 100644 --- a/README.md +++ b/README.md @@ -22,8 +22,6 @@ docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 ``` shell kubectl apply -f https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml; -或 -kubectl -n [指定的命名空间] apply -f https://github.com/justmine66/exceptionless-webhooks/blob/master/k8s/web.yml; ``` ## 2、配置 From 6dc25e4c8bed33f29b3f4fc8c6be49c08c4f1cff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Mon, 19 Nov 2018 13:51:58 +0800 Subject: [PATCH 39/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index f920434..2314196 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ 一个 Exceptionless 相关 WebHooks 项目。 # 目的 -当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),以便实时知晓线上程序运行情况。 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),实时地知晓运维报警提醒。 # 效果图 From 67e3a0b186e14f7b803a5d4dc3041f04842e5a08 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Mon, 19 Nov 2018 13:52:14 +0800 Subject: [PATCH 40/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 2314196..cd11590 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ 一个 Exceptionless 相关 WebHooks 项目。 # 目的 -当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),实时地知晓运维报警提醒。 +当Exceptionless触发配置的WebHooks通知类型时,如Error、LogError,发送消息到 DingTalk(钉钉),实时感知运维报警提醒。 # 效果图 From 681966b2a928328000a69767bc3193f5aec5a014 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=A0=E7=97=B4=E8=BF=B7=EF=BC=8C=E4=B8=8D=E6=88=90?= =?UTF-8?q?=E5=8A=9F?= <943299334@qq.com> Date: Mon, 26 Nov 2018 14:13:40 +0800 Subject: [PATCH 41/41] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index cd11590..4fbed20 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ ### docker ``` shell -docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0 +docker run -d -p 8000:80 justmine/exceptionless.api.webhook:0.0.0; ``` ### kubernetes(推荐)