构建ASP.NET MVC4+EF5+EasyUI+Unity2.x注入的后台管理系统(12)-系统日志和异常的处理②

简介: 原文:构建ASP.NET MVC4+EF5+EasyUI+Unity2.x注入的后台管理系统(12)-系统日志和异常的处理② 上一讲我们做了日志与异常的结果显示列表,这一节我们讲要把他应用系统中来。 首先我们在App.

原文:构建ASP.NET MVC4+EF5+EasyUI+Unity2.x注入的后台管理系统(12)-系统日志和异常的处理②

上一讲我们做了日志与异常的结果显示列表,这一节我们讲要把他应用系统中来。

首先我们在App.Common类库中创建一个通用类ResultHelper,这个类里面写了,获取一个GUID,获取当前时间,处理字符串等操作,虽然我们目前要用到的一个就是获取GUID但是以后我们可能还要用到别的,所以我都把他放进入了

然后在App.Admin创建一个核心文件夹,Core,放入LogHandler这个类是主要是写入日志,避免在每次都要实例化这个类,我把他封装起来,大家一看就知道。

然后修改Controller的Create方法,代码如下一一给出。

using System;
using System.Web;
using System.Text.RegularExpressions;

namespace App.Common
{
    public class ResultHelper
    {
        /// <summary>
        /// 创建一个全球唯一的32位ID
        /// </summary>
        /// <returns>ID串</returns>
        public static string NewId
        {
            get
            {
                string id = DateTime.Now.ToString("yyyyMMddHHmmssfffffff");
                string guid = Guid.NewGuid().ToString().Replace("-", "");
                id += guid.Substring(0, 10);
                return id;
            }
        }
        public static string NewTimeId
        {
            get
            {
                string id = DateTime.Now.ToString("yyyyMMddHHmmssfffffff");
                return id;
            }
        }
        /// <summary>
        /// 截取字符串
        /// </summary>
        /// <param name="value">字符串</param>
        /// <param name="length">剩下长度</param>
        /// <returns>指定字符串并加...</returns>
        public static string SubValue(string value, int length)
        {
            if (value.Length > length)
            {
                value = value.Substring(0, length); value = value + "..."; return NoHtml(value);
            }
            else { return NoHtml(value); }
        }
        //还原的时候
        public static string InputText(string inputString)
        {

            if ((inputString != null) && (inputString != String.Empty))
            {
                inputString = inputString.Trim();
                //if (inputString.Length > maxLength) 
                //inputString = inputString.Substring(0, maxLength); 
                inputString = inputString.Replace("<br>", "\n");
                inputString = inputString.Replace("&", "&amp");
                inputString = inputString.Replace("'", "''");
                inputString = inputString.Replace("<", "&lt");
                inputString = inputString.Replace(">", "&gt");
                inputString = inputString.Replace("chr(60)", "&lt");
                inputString = inputString.Replace("chr(37)", "&gt");
                inputString = inputString.Replace("\"", "&quot");
                inputString = inputString.Replace(";", ";");

                return inputString;
            }
            else
            {
                return "";
            }

        }
        //添加的时候
        public static string OutputText(string outputString)
        {

            if ((outputString != null) && (outputString != String.Empty))
            {
                outputString = outputString.Trim();
                outputString = outputString.Replace("&amp", "&");
                outputString = outputString.Replace("''", "'");
                outputString = outputString.Replace("&lt", "<");
                outputString = outputString.Replace("&gt", ">");
                outputString = outputString.Replace("&lt", "chr(60)");
                outputString = outputString.Replace("&gt", "chr(37)");
                outputString = outputString.Replace("&quot", "\"");
                outputString = outputString.Replace(";", ";");
                outputString = outputString.Replace("\n", "<br>");
                return outputString;
            }
            else
            {
                return "";
            }
        }
        /// <summary>
        /// 去除HTML标记
        /// </summary>
        /// <param name="NoHTML">包括HTML的源码 </param>
        /// <returns>已经去除后的文字</returns>
        public static string NoHtml(string Htmlstring)
        {
            //删除脚本
            Htmlstring = Regex.Replace(Htmlstring, @"<script[^>]*?>.*?</script>", "", RegexOptions.IgnoreCase);
            //删除HTML
            Htmlstring = Regex.Replace(Htmlstring, @"<(.[^>]*)>", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"([\r\n])[\s]+", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"-->", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"<!--.*", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(quot|#34);", "\"", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(amp|#38);", "&", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(lt|#60);", "<", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(gt|#62);", ">", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(nbsp|#160);", " ", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(iexcl|#161);", "\xa1", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(cent|#162);", "\xa2", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(pound|#163);", "\xa3", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&(copy|#169);", "\xa9", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&#(\d+);", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&hellip;", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&mdash;", "", RegexOptions.IgnoreCase);
            Htmlstring = Regex.Replace(Htmlstring, @"&ldquo;", "", RegexOptions.IgnoreCase);
            Htmlstring.Replace("<", "");
            Htmlstring = Regex.Replace(Htmlstring, @"&rdquo;", "", RegexOptions.IgnoreCase);
            Htmlstring.Replace(">", "");
            Htmlstring.Replace("\r\n", "");
            Htmlstring = HttpContext.Current.Server.HtmlEncode(Htmlstring).Trim();
            return Htmlstring;

        }
        /// <summary>
        /// 格式化文本(防止SQL注入)
        /// </summary>
        /// <param name="str"></param>
        /// <returns></returns>
        public static string Formatstr(string html)
        {
            System.Text.RegularExpressions.Regex regex1 = new System.Text.RegularExpressions.Regex(@"<script[\s\S]+</script *>", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex2 = new System.Text.RegularExpressions.Regex(@" href *= *[\s\S]*script *:", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex3 = new System.Text.RegularExpressions.Regex(@" on[\s\S]*=", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex4 = new System.Text.RegularExpressions.Regex(@"<iframe[\s\S]+</iframe *>", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex5 = new System.Text.RegularExpressions.Regex(@"<frameset[\s\S]+</frameset *>", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex10 = new System.Text.RegularExpressions.Regex(@"select", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex11 = new System.Text.RegularExpressions.Regex(@"update", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            System.Text.RegularExpressions.Regex regex12 = new System.Text.RegularExpressions.Regex(@"delete", System.Text.RegularExpressions.RegexOptions.IgnoreCase);
            html = regex1.Replace(html, ""); //过滤<script></script>标记
            html = regex2.Replace(html, ""); //过滤href=javascript: (<A>) 属性
            html = regex3.Replace(html, " _disibledevent="); //过滤其它控件的on...事件
            html = regex4.Replace(html, ""); //过滤iframe
            html = regex10.Replace(html, "s_elect");
            html = regex11.Replace(html, "u_pudate");
            html = regex12.Replace(html, "d_elete");
            html = html.Replace("'", "");
            html = html.Replace("&nbsp;", " ");
            return html;
        }
        /// <summary>
        /// 检查SQL语句合法性
        /// </summary>
        /// <param name="sql"></param>
        /// <returns></returns>
        public static bool ValidateSQL(string sql, ref string msg)
        {
            if (sql.ToLower().IndexOf("delete") > 0)
            {
                msg = "查询参数中含有非法语句DELETE";
                return false;
            }
            if (sql.ToLower().IndexOf("update") > 0)
            {
                msg = "查询参数中含有非法语句UPDATE";
                return false;
            }

            if (sql.ToLower().IndexOf("insert") > 0)
            {
                msg = "查询参数中含有非法语句INSERT";
                return false;
            }
            return true;
        }
        //获取当前时间
        public static DateTime NowTime
        {
            get 
            {
                return DateTime.Now;
            }
        }

        /// <summary>
        /// 将日期转换成字符串
        /// </summary>
        /// <param name="dt">日期</param>
        /// <returns>字符串</returns>
        public static string DateTimeConvertString(DateTime? dt)
        {
            if (dt == null)
            {
                return "";
            }
            else
            {
                return Convert.ToDateTime(dt.ToString()).ToShortDateString();
            }
        }
        /// <summary>
        /// 将字符串转换成日期
        /// </summary>
        /// <param name="str">字符串</param>
        /// <returns>日期</returns>
        public static DateTime? StringConvertDatetime(string str)
        {
            if (str == null)
            {
                return null ;
            }
            else
            {
                try
                {
                    return Convert.ToDateTime(str);
                }
                catch {
                    return null;
                }
            }
        }

        public static string GetUserIP()
        {
            if (System.Web.HttpContext.Current.Request.ServerVariables["HTTP_VIA"] != null)
                return System.Web.HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"].Split(new char[] { ',' })[0];
            else
                return System.Web.HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];
        }
    }
}
ResultHelper
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using App.Common;
using App.DAL;
using App.IBLL;
using App.Models;
using Microsoft.Practices.Unity;

namespace App.Admin
{
    public static class LogHandler
    {
        [Dependency]
        public static ISysLogBLL logBLL { get; set; }
        /// <summary>
        /// 写入日志
        /// </summary>
        /// <param name="oper">操作人</param>
        /// <param name="mes">操作信息</param>
        /// <param name="result">结果</param>
        /// <param name="type">类型</param>
        /// <param name="module">操作模块</param>
        public static void WriteServiceLog(string oper, string mes, string result, string type, string module)
        {
           
               
                SysLog entity = new SysLog();
                entity.Id = ResultHelper.NewId;
                entity.Operator = oper;
                entity.Message = mes;
                entity.Result = result;
                entity.Type = type;
                entity.Module = module;
                entity.CreateTime = ResultHelper.NowTime;
                using (SysLogRepository logRepository = new SysLogRepository())
                {
                    logRepository.Create(entity);
                }
        
        }
    }
}
LogHandler
 [HttpPost]
        public JsonResult Create(SysSampleModel model)
        {


                if (m_BLL.Create(model))
                {
                    LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name, "成功", "创建", "样例程序");
                    return Json(1, JsonRequestBehavior.AllowGet);
                }
                else
                {
                    LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name, "失败", "创建", "样例程序");
                    return Json(0, JsonRequestBehavior.AllowGet);
                }
     
        }
SysSampleController

同时App.Common要引用程序集System.Web

运行添加一条记录,然后打开我们的日志模块,OK,日志记录完成了,有点简单。

接下来是异常,上一讲说到,异常我们放在BLL中处理,然后我们把错误或者异常信息返回到Controller中被日志记录,当然异常他是在BLL层被记录的。

我们需要一个异常的集合类,来记录BLL层和DAL层,有时候DAL也要处理异常,所以我们也要用到ref 引用传递,貌似ref我们很喜欢,呵呵

见代码,在App.Common创建一个异常集合类

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace App.Common
{
    public class ValidationError
    {
        public ValidationError() { }
        public string ErrorMessage { get; set; }
       
    }
    public class ValidationErrors : List<ValidationError>
    {
        /// <summary>
        /// 添加错误
        /// </summary>
        /// <param name="errorMessage">信息描述</param>
        public void Add(string errorMessage)
        {
            base.Add(new ValidationError { ErrorMessage = errorMessage });
        }
        /// <summary>
        /// 获取错误集合
        /// </summary>
        public string Error
        {
            get {
                string error = "";
                this.All(a => {
                    error += a.ErrorMessage;
                    return true;
                });
                return error;
            } 
        }
    }
}
ValidationErrorHelper.cs

我们也要创建一个封装好的异常写入,类似与Log的LogHandler封装但我们放在BLL中,因为我们以后的其他项目的BLL要引用,这一步要考虑到。
在BLL中创建文件夹Core,写入以下类,BLL引用程序集System.Web里面用到了http的一些方法

using System;
using System.Web.Configuration;
using App.Models;
using System.IO;
using System.Text;
using App.Common;

namespace App.BLL.Core
{

        /// <summary>
        /// 写入一个异常错误
        /// </summary>
        /// <param name="ex">异常</param>
        public static class ExceptionHander
        {
            /// <summary>
            /// 加入异常日志
            /// </summary>
            /// <param name="ex">异常</param>
            public static void WriteException(Exception ex)
            {
               
                    try
                    {
                        using (DBContainer db = new DBContainer())
                        {
                            SysException model = new SysException()
                            {
                                Id = ResultHelper.NewId,
                                HelpLink = ex.HelpLink,
                                Message = ex.Message,
                                Source = ex.Source,
                                StackTrace = ex.StackTrace,
                                TargetSite = ex.TargetSite.ToString(),
                                Data =ex.Data.ToString(),
                                CreateTime = ResultHelper.NowTime
                                
                            };
                            db.SysException.AddObject(model);
                            db.SaveChanges();
                        }
                    }
                    catch (Exception ep)
                    {
                        try
                        {
                            //异常失败写入txt
                            string path = @"~/exceptionLog.txt";
                            string txtPath = System.Web.HttpContext.Current.Server.MapPath(path);//获取绝对路径
                            using (StreamWriter sw = new StreamWriter(txtPath, true, Encoding.Default))
                            {
                                sw.WriteLine((ex.Message + "|" + ex.StackTrace + "|" + ep.Message + "|" + DateTime.Now.ToString()).ToString());
                                sw.Dispose();
                                sw.Close();
                            }
                            return;
                        }
                        catch { return; }
                    }

                

            }
        }

    
}
ExceptionHander

此异常当处理也异常时候,将在网站根目录下写入一个txt文件。
创建一个全局变量

ValidationErrors errors = new ValidationErrors();

我们要用引用传递,所以要修改IBLL和BLL的Create方法,如下
ISysSampleBLL  :  bool Create(ref ValidationErrors errors, SysSampleModel model);

SysSampleBLL   :

 /// <summary>
        /// 创建一个实体
        /// </summary>
        /// <param name="errors">持久的错误信息</param>
        /// <param name="model">模型</param>
        /// <returns>是否成功</returns>
        /// <summary>
        /// 创建一个实体
        /// </summary>
        /// <param name="errors">持久的错误信息</param>
        /// <param name="model">模型</param>
        /// <returns>是否成功</returns>
        public bool Create(ref ValidationErrors errors, SysSampleModel model)
        {
            try
            {
                SysSample entity = Rep.GetById(model.Id);
                if (entity != null)
                {
                    errors.Add("主键重复");
                    return false;
                }
                entity = new SysSample();
                entity.Id = model.Id;
                entity.Name = model.Name;
                entity.Age = model.Age;
                entity.Bir = model.Bir;
                entity.Photo = model.Photo;
                entity.Note = model.Note;
                entity.CreateTime = model.CreateTime;

                if (Rep.Create(entity) == 1)
                {
                    return true;
                }
                else
                {
                    errors.Add("插入失败");
                    return false;
                }
            }
            catch (Exception ex)
            {
                errors.Add(ex.Message);
                ExceptionHander.WriteException(ex);
                return false;
            }
        }

修改Controller

 [HttpPost]
        public JsonResult Create(SysSampleModel model)
        {
                if (m_BLL.Create(ref errors, model))
                {
                    LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name, "成功", "创建", "样例程序");
                    return Json(1, JsonRequestBehavior.AllowGet);
                }
                else
                {
                    string ErrorCol = errors.Error;
                    LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name + "," + ErrorCol, "失败", "创建", "样例程序");
                    return Json(0, JsonRequestBehavior.AllowGet);
                }
     
        }

 注意:ExceptionHander.WriteException(ex);这里是写入异常信息

OK,你现在可以创建一条新的记录和插入一个ID大于50个字符的记录,让他记录日志和异常了。

显然我们的失败错误提示已经不符合国情了。我们返回的json格式是0和1我们要返回多个值了,比如1和成功创建,0和失败了啊,这样的2个值怎么办?

controller能把datagrid传过来的东西用类来接受,那么反过来想,js也能把controller发出去的值分解,创建一个序列化的类

在App.Common类库中创建JsonHandler帮助类,里面有2个重载,一个是返回3个值一个是2个值的。

所以当我们要返回订单的数量和总价格的时候,我们将用到类似的手段

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace App.Common
{
    public class JsonHandler
    {

        public static JsonMessage CreateMessage(int ptype,string pmessage,string pvalue)
        {
            JsonMessage json = new JsonMessage()
            {
                type = ptype,
                message = pmessage,
                value = pvalue
            };
            return json;
        }
        public static JsonMessage CreateMessage(int ptype, string pmessage)
        {
            JsonMessage json = new JsonMessage()
            {
                type = ptype,
                message = pmessage,
            };
            return json;
        }
    }

    public class JsonMessage
    {
        public int type{get;set;}
        public string message{get;set;}
        public string value{get;set;}
    }
}
JsonHandler

再次修改Controller的Create

  [HttpPost]
        public JsonResult Create(SysSampleModel model)
        {
            if (m_BLL.Create(ref errors, model))
            {
                LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name, "成功", "创建", "样例程序");
                return Json(JsonHandler.CreateMessage(1, "插入成功"), JsonRequestBehavior.AllowGet);
            }
            else
            {
                string ErrorCol = errors.Error;
                LogHandler.WriteServiceLog("虚拟用户", "Id:" + model.Id + ",Name:" + model.Name + "," + ErrorCol, "失败", "创建", "样例程序");
                return Json(JsonHandler.CreateMessage(0, "插入失败" + ErrorCol), JsonRequestBehavior.AllowGet);
            }
     
        }

修改SysSample的Create的JS部分

<script type="text/javascript">
    $(function () {
        $("#btnSave").click(function () {
            if ($("#CreateForm").valid()) {
                $.ajax({
                    url: "/SysSample/Create",
                    type: "Post",
                    data: $("#CreateForm").serialize(),
                    dataType: "json",
                    success: function (data) {
                        if (data.type == 1) {
                            window.parent.frameReturnByMes(data.message);
                            window.parent.frameReturnByReload(true);
                            window.parent.frameReturnByClose()
                        }
                        else {
                            window.parent.frameReturnByMes(data.message);
                        }
                    }
                });
            }
            return false;
        });
    });
    </script>

 

由于时间关系,这一讲就先到这里吧!这一讲其实比较仓促。不懂的留言

你需要继续做的就是在删除,编辑等操作也加入这些的。这点留给大家自己表现吧....

下一讲是全局异常的捕获。

相关实践学习
【涂鸦即艺术】基于云应用开发平台CAP部署AI实时生图绘板
【涂鸦即艺术】基于云应用开发平台CAP部署AI实时生图绘板
目录
相关文章
|
7月前
|
SQL 人工智能 监控
SLS Copilot 实践:基于 SLS 灵活构建 LLM 应用的数据基础设施
本文将分享我们在构建 SLS SQL Copilot 过程中的工程实践,展示如何基于阿里云 SLS 打造一套完整的 LLM 应用数据基础设施。
2055 96
|
8月前
|
存储 运维 监控
金蝶云•星辰基于 SLS 构建稳定高效可观测系统
金蝶云•星辰通过阿里云日志服务 SLS 替换自建 ELK 系统,构建统一可观测平台,有效应对业务高速增长带来的稳定性挑战,提升运维效率与系统稳定性,助力企业数字化转型。
|
存储 消息中间件 缓存
MiniMax GenAI 可观测性分析 :基于阿里云 SelectDB 构建 PB 级别日志系统
基于阿里云SelectDB,MiniMax构建了覆盖国内及海外业务的日志可观测中台,总体数据规模超过数PB,日均新增日志写入量达数百TB。系统在P95分位查询场景下的响应时间小于3秒,峰值时刻实现了超过10GB/s的读写吞吐。通过存算分离、高压缩比算法和单副本热缓存等技术手段,MiniMax在优化性能的同时显著降低了建设成本,计算资源用量降低40%,热数据存储用量降低50%,为未来业务的高速发展和技术演进奠定了坚实基础。
581 1
MiniMax GenAI 可观测性分析 :基于阿里云 SelectDB 构建 PB 级别日志系统
|
存储 运维 监控
超越传统模型:从零开始构建高效的日志分析平台——基于Elasticsearch的实战指南
【10月更文挑战第8天】随着互联网应用和微服务架构的普及,系统产生的日志数据量日益增长。有效地收集、存储、检索和分析这些日志对于监控系统健康状态、快速定位问题以及优化性能至关重要。Elasticsearch 作为一种分布式的搜索和分析引擎,以其强大的全文检索能力和实时数据分析能力成为日志处理的理想选择。
1103 6
|
存储 数据采集 数据处理
【Flume拓扑揭秘】掌握Flume的四大常用结构,构建强大的日志收集系统!
【8月更文挑战第24天】Apache Flume是一个强大的工具,专为大规模日志数据的收集、聚合及传输设计。其核心架构包括源(Source)、通道(Channel)与接收器(Sink)。Flume支持多样化的拓扑结构以适应不同需求,包括单层、扇入(Fan-in)、扇出(Fan-out)及复杂多层拓扑。单层拓扑简单直观,适用于单一数据流场景;扇入结构集中处理多源头数据;扇出结构则实现数据多目的地分发;复杂多层拓扑提供高度灵活性,适合多层次数据处理。通过灵活配置,Flume能够高效构建各种规模的数据收集系统。
448 0
|
敏捷开发 前端开发 测试技术
阿里云云效产品使用合集之如何将云效构建执行过程中产生的日志通过邮件发送
云效作为一款全面覆盖研发全生命周期管理的云端效能平台,致力于帮助企业实现高效协同、敏捷研发和持续交付。本合集收集整理了用户在使用云效过程中遇到的常见问题,问题涉及项目创建与管理、需求规划与迭代、代码托管与版本控制、自动化测试、持续集成与发布等方面。
|
消息中间件 监控 Kafka
Filebeat+Kafka+Logstash+Elasticsearch+Kibana 构建日志分析系统
【8月更文挑战第13天】Filebeat+Kafka+Logstash+Elasticsearch+Kibana 构建日志分析系统
1480 3
|
Java 开发者
构建健壮的Java应用:错误处理与日志管理
构建健壮的Java应用:错误处理与日志管理
|
Java API Apache
项目构建时抛出LoggerContextShutdownAware log 错误问题处理
SpringBoot应用的日志显示它尝试初始化Skywalking日志目录为/app/logs/skywalking。随后,应用程序一个异常,具体是`java.lang.reflect.InvocationTargetException`。问题可能是由于日志库的冲突或缺失导致的。建议检查项目中是否存在与SpringBoot内置日志系统冲突的自定义日志配置,并确保所有必要的日志依赖,如log4j-core和log4j-api,都已正确且版本匹配地引入。通过解决这些冲突并重新构建,应该可以解决这个问题。
414 0
|
存储 监控 Kubernetes
构建高效稳定的云原生日志监控系统
【5月更文挑战第26天】 随着微服务架构和容器化技术的普及,传统的日志监控方法面临重大挑战。本文将探讨如何构建一个既高效又稳定的云原生日志监控系统,该系统旨在提供实时的日志分析能力,同时保证系统的高可用性和可扩展性。我们将讨论利用现代技术栈如Fluentd、Elasticsearch和Kibana(EFK栈)来搭建日志收集、存储和可视化的解决方案,并深入探讨如何通过容器编排工具如Kubernetes来实现日志服务的自动伸缩和故障恢复。此外,我们还将介绍一些最佳实践,帮助运维团队在保持系统性能的同时,降低资源消耗和运营成本。
下一篇
开通oss服务