缩短告警信息里面的时间显示
大石头 authored at 2022-02-23 22:24:23
2.53 KiB
Stardust
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Http;
using NewLife;
using NewLife.Log;
using Stardust.Server.Common;
using XCode.Membership;

namespace Stardust.Server.Middlewares
{
    /// <summary>性能追踪中间件</summary>
    public class TracerMiddleware
    {
        private readonly RequestDelegate _next;

        /// <summary>追踪器</summary>
        public static ITracer Tracer { get; set; }

        /// <summary>实例化</summary>
        /// <param name="next"></param>
        public TracerMiddleware(RequestDelegate next)
        {
            _next = next ?? throw new ArgumentNullException(nameof(next));
        }

        /// <summary>调用</summary>
        /// <param name="ctx"></param>
        /// <returns></returns>
        public async Task Invoke(HttpContext ctx)
        {
            // APM追踪
            //var span = Tracer?.NewSpan(ctx.Request.Path);
            ISpan span = null;
            if (Tracer != null)
            {
                var action = GetAction(ctx);
                if (!action.IsNullOrEmpty())
                {
                    span = Tracer.NewSpan(action);
                    span.Detach(ctx.Request.Headers.ToDictionary(e => e.Key, e => (Object)e.Value));
                }
            }

            ManageProvider.UserHost = ctx.GetUserHost();
            try
            {
                await _next.Invoke(ctx);
            }
            catch (Exception ex)
            {
                span?.SetError(ex, ctx.Request.QueryString + "");

                throw;
            }
            finally
            {
                ManageProvider.UserHost = null;
                span?.Dispose();
            }
        }

        /// <summary>忽略的后缀</summary>
        public static String[] ExcludeSuffixes { get; set; } = new[] {
            ".html", ".htm", ".js", ".css", ".png", ".jpg", ".gif", ".ico",  // 脚本样式图片
            ".woff", ".woff2", ".svg", ".ttf", ".otf", ".eot"   // 字体
        };

        private static String GetAction(HttpContext ctx)
        {
            var p = ctx.Request.Path + "";
            if (p.EndsWithIgnoreCase(ExcludeSuffixes)) return null;

            var ss = p.Split('/');
            if (ss.Length == 0) return p;

            // 如果最后一段是数字,则可能是参数,需要去掉
            if ((ss.Length == 4 || ss.Length == 5) && ss[ss.Length - 1].ToInt() > 0) p = "/" + ss.Take(ss.Length - 1).Join("/");

            return p;
        }
    }
}