JavaRush /Java 博客 /Random-ZH /Java 日志记录。展开 strace 球

Java 日志记录。展开 strace 球

已在 Random-ZH 群组中发布
“下午好,今天工业现场记录到了一起事件,请开发商加入分析小组。” 你一天的工作可能会从这样的事情开始,也可能是早上——这并不重要。但让我们从头开始。通过在 JavaRush 中解决问题,您将学会编写有效的代码并执行预期的操作。如果您查看帮助部分,很明显,第一次并不总是有效。在工作中也是如此。你并不总是能在第一次就解决问题:错误是我们永恒的伴侣。重要的是您可以恢复错误的事件。 记录。 展开 stectrace 球 - 1让我们从一个例子开始。让我们假设您是一名警察。您被叫到事件现场(商店的玻璃被打破),您到达了,他们正在等待您对所发生事件的答复。从哪里开始?我不知道警察是怎么工作的。非常有条件 - 他们开始寻找证人、证据和所有这些东西。如果这个地方本身可以详细告诉你发生了什么事怎么办?例如,像这样:
  • 21:59 主人打开警报(5分钟后完全激活)
  • 22:00 业主关门
  • 22:05 警报全面启动
  • 22:06 主人拉动把手
  • 23:15 噪音传感器开启
  • 23:15 一群狗跑过去,大声吠叫
  • 23:15 噪音传感器关闭
  • 01:17 展示柜外玻璃上的震动传感器开启
  • 01:17 一只鸽子飞进玻璃杯
  • 01:17 玻璃碎了
  • 01:17 警笛响起
  • 01:17 鸽子摆脱束缚飞走
好吧,你不必深入研究这些细节;发生了什么就立刻清楚了。开发中也是如此。当你可以从录音中得知发生了什么时,这真是太酷了。现在您可能还记得调试,因为您可以调试所有内容。但不是。你回到家,晚上一切都坏了,没有什么可以调试的:你需要了解它坏掉的原因并修复它。这就是日志发挥作用的地方,它记录了一夜之间发生的一切的历史。在这篇文章的过程中,我建议你想一下,每个听(看)新闻的人可能都听说过的最著名的记录器之一(不是真正的记录器,更像是监控)是什么?感谢他,一些事件得以恢复。现在让我们严肃点吧。Java 中的日志记录是记录代码中发生的任何事件的过程。作为一名程序员,你有责任写下你的代码做了什么,因为这样这些日志就会提供给你进行分析。如果一切都做得好,那么任何错误都会很快被整理和修复。在这里,我可能不会深究到底有哪些记录器。在这篇文章中,我们将把自己限制在简单的范围内java.util.Logger:这对于相互了解来说已经足够了。每个日志条目包含日期时间、事件级别、消息。日期和时间是自动输入的。事件级别由消息作者选择。有几个层次。主要是信息、调试、错误。
  • 信息 - 通常这些是有关正在发生的事情的信息消息,类似于日期的历史记录:1915 - 发生了一些事情,1916 - 发生了其他事情。
  • DEBUG - 更详细地描述特定时刻的事件。例如,历史上的一场战斗的细节都是调试级别
  • ERROR - 发生的错误通常写在这里。您可能已经注意到,当您将某些内容包装在 中时try-catch,该块catch会被替换为e.printStacktrace()。它仅将条目输出到控制台。使用记录器,您可以将此条目发送到记录器(哈哈),您明白了。
  • WARN - 警告写在这里。例如,汽车中的过热灯。这只是一个警告,最好改变一些东西,但这还不是故障。当机器出现故障时,我们将记录错误级别。
我们已经整理好了等级。但别担心:它们之间的界限很窄——不是每个人都能解释它。另外,它可能因项目而异。高级开发人员将向您解释什么级别以及要记录什么。最主要的是这些记录足够你以后分析了。这是即时理解的。接下来是设置。记录器可以被告知写入位置(控制台、文件、jms 或其他地方),并指定级别(信息、错误、调试...)。 我们的简单记录器的设置示例如下所示:
handlers = java.util.logging.FileHandler, java.util.logging.ConsoleHandler

java.util.logging.FileHandler.level     = INFO
java.util.logging.FileHandler.formatter = java.util.logging.SimpleFormatter
java.util.logging.FileHandler.append    = true
java.util.logging.FileHandler.pattern   = log.%u.%g.txt

java.util.logging.ConsoleHandler.level     = INFO
java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
在这种情况下,所有内容都经过配置,以便记录器同时写入文件和控制台。在这种情况下?如果控制台中删除了某些内容,而且按文件搜索会更容易。两者的信息级别。还为该文件指定了名称模式。这是一个最小的配置,允许您同时写入控制台和文件。 java.util.logging.FileHandler.append设置为true以便文件中的旧条目不会被删除。使用示例如下(没有注释,记录器对自身进行注释):
public class Main {
    static Logger LOGGER;
    static {
        try(FileInputStream ins = new FileInputStream("C:\\log.config")){ \\полный путь до file с конфигами
            LogManager.getLogManager().readConfiguration(ins);
            LOGGER = Logger.getLogger(Main.class.getName());
        }catch (Exception ignore){
            ignore.printStackTrace();
        }
    }
    public static void main(String[] args) {
        try {
            LOGGER.log(Level.INFO,"Начало main, создаем лист с типизацией Integers");
            List<Integer> ints = new ArrayList<Integer>();
            LOGGER.log(Level.INFO,"присваиваем лист Integers листу без типипзации");
            List empty = ints;
            LOGGER.log(Level.INFO,"присваиваем лист без типипзации листу строк");
            List<String> string = empty;
            LOGGER.log(Level.WARNING,"добавляем строку \"бла бла\" в наш переприсвоенный лист, возможна ошибка");
            string.add("бла бла");
            LOGGER.log(Level.WARNING,"добавляем строку \"бла 23\" в наш переприсвоенный лист, возможна ошибка");
            string.add("бла 23");
            LOGGER.log(Level.WARNING,"добавляем строку \"бла 34\" в наш переприсвоенный лист, возможна ошибка");
            string.add("бла 34");


            LOGGER.log(Level.INFO,"выводим все элементы листа с типизацией Integers в консоль");
            for (Object anInt : ints) {
                System.out.println(anInt);
            }

            LOGGER.log(Level.INFO,"Размер equals " + ints.size());
            LOGGER.log(Level.INFO,"Получим первый элемент");
            Integer integer = ints.get(0);
            LOGGER.log(Level.INFO,"выведем его в консоль");
            System.out.println(integer);

        }catch (Exception e){
            LOGGER.log(Level.WARNING,"что-то пошло не так" , e);
        }
    }
}
这不是最好的例子,我举了手边的一个。输出示例:
апр 19, 2019 1:10:14 AM generics.Main main
INFO: Начало main, создаем лист с типизацией Integers
апр 19, 2019 1:10:14 AM generics.Main main
INFO: присваиваем лист Integers листу без типипзации
апр 19, 2019 1:10:14 AM generics.Main main
INFO: присваиваем лист без типипзации листу строк
апр 19, 2019 1:10:14 AM generics.Main main
WARNING: добавляем строку "бла бла" в наш переприсвоенный лист, возможна ошибка
апр 19, 2019 1:10:14 AM generics.Main main
WARNING: добавляем строку "бла 23" в наш переприсвоенный лист, возможна ошибка
апр 19, 2019 1:10:14 AM generics.Main main
WARNING: добавляем строку "бла 34" в наш переприсвоенный лист, возможна ошибка
апр 19, 2019 1:10:14 AM generics.Main main
INFO: выводим все элементы листа с типизацией Integers в консоль
апр 19, 2019 1:10:14 AM generics.Main main
INFO: Размер equals 3
апр 19, 2019 1:10:14 AM generics.Main main
INFO: Получим первый элемент
апр 19, 2019 1:10:14 AM generics.Main main
WARNING: что-то пошло не так
java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Integer
	at generics.Main.main(Main.java:45)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:498)
	at com.intellij.rt.execution.application.AppMain.main(AppMain.java:147)
这里我想重点说一下笔记:
апр 19, 2019 1:10:14 AM generics.Main main
INFO: Размер equals 3
апр 19, 2019 1:10:14 AM generics.Main main
INFO: Получим первый элемент
这篇文章毫无用处,而且没有提供任何信息。就像错误条目一样:
WARNING: что-то пошло не так
你不应该这样写:它只是为了日志而日志,它只会造成妨碍。尝试总是写有意义的事情。 我认为这足以停止使用它System.out.println并转向成人玩具。它java.util.logging有缺点。例如,我上面描述的级别不在这里,但它们在大多数使用的记录器中。我在本文中选择它是java.util.logging因为它不需要对连接进行额外的操作。我还要指出的是,它可以用来代替 这里已经出现的缺点之一: LOGGER.info-它允许您传输消息和对象,记录器本身会将其精美地写下来。同时,它只接收一条消息,即 异常无法传递,必须自己翻译成字符串。我希望这个示例足以让您熟悉 Java 日志记录。然后你可以连接其他记录器(log4j、slf4j、Logback...)——它们有很多,但本质是相同的^来记录操作的历史。 官方教程LOGGER.log(Level.INFO...LOGGER.log(Level.WARNING,"что-то пошло не так" , e);ExceptionLOGGER.warning("");
评论
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION