Log4j 2.x XSD的描述不完整

在博客文章JAXB和Log4j XML配置文件中 ,我讨论了“与使用JAXB通过Java类处理[Log4j 1.x和Log4j 2.x] XML配置文件相关的细微差别。” 在本文中,我将探讨另一个与通过Log4j 2.x XML Schema文件Log4j-config.xsd生成的JAXB对象生成Log4j 2.x配置XML相关的挑战:它没有完全指定Log4j 2.x组件的配置特点。

使用Log4j 2.x XML配置时 ,首先要做出的重要区别之一是要使用XML的“ 风味 ”(“简洁”或“严格”)。 简洁的格式可能更容易,因为XML元素的名称对应于它们表示的Log4j 2组件,但是XSD仅支持严格格式。 这意味着从Log4j 2.x XSD生成的JAXB对象中编组的任何XML都必须具有“严格”格式,而不是“简洁”格式。

不幸的是,当前与Log4j 2.x发行版一起提供的XSD( Log4j-config.xsd )不足以生成Log4j 2支持的完整“严格” XML配置。我在这里通过讨论XSD定义的复杂类型来演示这一点。 “ AppenderType ”,因为它是受支持元素在XSD中缺少其潜在属性规范的最极端情况之一。 从Log4j 2.6.2开始,下面的代码清单显示了Log4j-config.xsdAppenderType的定义。

在Log4j 2.6.2的Log4j-config.xsd定义的AppenderType

<xs:complexType name="AppenderType"><xs:sequence><xs:element name="Layout" type="LayoutType" minOccurs="0"/><xs:choice minOccurs="0" maxOccurs="1"><xs:element name="Filters" type="FiltersType"/><xs:element name="Filter" type="FilterType"/></xs:choice></xs:sequence><xs:attribute name="type" type="xs:string" use="required"/><xs:attribute name="name" type="xs:string" use="required"/><xs:attribute name="fileName" type="xs:string" use="optional"/>
</xs:complexType>

刚刚显示的XSD的摘录告诉我们,以XSD兼容的XML描述的附加器将只能具有三个属性( typenamefileName )中的一个或多个。 “ type ”属性用于标识其附加器的类型(例如“ File ”,“ RollingFile ”,“ Console ”,“ Socket ”和“ Syslog ”)。 问题在于,每个追加程序的“类型”都有不同的属性和特性,理想情况下,可以通过此AppenderType上的属性来描述。

有关Appender的Log4j 2.x文档列出了不同类型的附加程序的特征。 例如,此页面指示ConsoleAppender具有七个参数: filterlayoutfollowdirectnameignoreExceptionstarget 。 该name是由一般所支持的属性之一AppenderType复杂类型和filterlayout通过在嵌套的元件支撑AppenderType 。 但是,可用于ConsoleAppender的其他四个参数在XSD中没有规定定义它们的机制。

甚至不考虑自定义Log4j 2.x附加程序 , 内置的Log4j 2.x附加程序不会共享相同的属性和特征,并且大多数属性具有比AppenderType指定的三个属性和两个嵌套元素更多的特征。 我讨论的七个参数的控制台追加程序以前和其他例子包括RollingFileAppender进行其12个参数( appendbufferedIObufferSizefilterfileNamefilePatternimmediateFlushlayoutnamepolicystrategyignoreExceptions )的JDBCAppender与七个参数( nameignoreExceptionsfilterbufferSizeconnectionSourcetableNamecolumnConfigs )和JMSAppender及其十三个参数( factoryBindingNamefactoryNamefilterlayoutnamepasswordproviderURLdestinationBindingNamesecurityPrincipalNamesecurityCredentialsignoreExceptionsurlPkgPrefixesuserName )。

为了描述XSD中给定的附加器类型可用的每个参数,都需要XML Schema具备以下能力:编写一组特定的可用属性取决于AppenderTypetype属性的设置。 不幸的是,XML Schema不容易支持这种条件规范,在该条件规范中,给定复杂类型的可用属性基于复杂类型的其他属性之一而不同。

由于模式语言的局限性,想要使用JAXB生成对所有提供的附加程序均具有完全支持的对象的人将需要更改XSD。 一种方法是更改​​XSD,以使AppenderType具有任何内置附加程序的所有可能属性,这些附加属性可用作元素的可选属性。 最明显的缺点是,即使该属性不适用于特定的附加程序类型,XSD也会允许任何附加程序类型具有任何属性。 但是,这种方法将允许JAXB生成的对象将给定附加类型的所有XML属性编组起来。 下一个代码段说明了如何开始。 此处指定了一些不同的追加器所需的其他属性,但是即使更长的列表也不包含支持所有可能的内置追加器类型的属性所需的所有可能的追加器属性。

一些添加到AppenderType Appender属性

<xs:complexType name="AppenderType"><xs:sequence><xs:element name="Layout" type="LayoutType" minOccurs="0"/><xs:choice minOccurs="0" maxOccurs="1"><xs:element name="Filters" type="FiltersType"/><xs:element name="Filter" type="FilterType"/></xs:choice></xs:sequence><xs:attribute name="type" type="xs:string" use="required"/><xs:attribute name="name" type="xs:string" use="required"/><xs:attribute name="fileName" type="xs:string" use="optional"/><!-- Attributes specified below here are not in Log4j 2.x Log4j-config.xsd --><xs:attribute name="target" type="xs:string" use="optional"/><xs:attribute name="follow" type="xs:string" use="optional"/><xs:attribute name="append" type="xs:string" use="optional"/><xs:attribute name="filePattern" type="xs:string" use="optional"/><xs:attribute name="host" type="xs:string" use="optional"/><xs:attribute name="port" type="xs:string" use="optional"/><xs:attribute name="protocol" type="xs:string" use="optional"/><xs:attribute name="connectTimeoutMillis" type="xs:integer" use="optional"/><xs:attribute name="reconnectionDelayMillis" type="xs:string" use="optional"/><xs:attribute name="facility" type="xs:string" use="optional"/><xs:attribute name="id" type="xs:string" use="optional"/><xs:attribute name="enterpriseNumber" type="xs:integer" use="optional"/><xs:attribute name="useMdc" type="xs:boolean" use="optional"/><xs:attribute name="mdcId" type="xs:string" use="optional"/><xs:attribute name="mdcPrefix" type="xs:string" use="optional"/><xs:attribute name="eventPrefix" type="xs:string" use="optional"/><xs:attribute name="newLine" type="xs:boolean" use="optional"/><xs:attribute name="newLineEscape" type="xs:string" use="optional"/>
</xs:complexType>

更改Log4j 2.x XSD以完全支持所有内置附加程序的第二种方法是将XSD设计从具有由type属性指定的特定类型的单个AppenderType更改为具有许多不同的复杂类型,每个复杂类型分别表示不同的XSD设计。内置的附加器类型。 使用这种方法,XSD可以强制执行任何给定附加程序的所有属性,并且仅与该给定附加程序相关联的属性。 每个追加程序都具有元素类型的这种方法类似于“简洁” XML格式的工作方式,但是当前没有XSD支持。

请注意,我在这里有意专注于内置的附加器类型,因为可以期望静态XSD能够合理,充分且完全地支持它。 另外:可以通过为属性指定任意的名称/值对来支持此操作,就像对过滤器或参数进行的操作一样 ,但是这还导致能够指定多余的甚至是无用的属性,而架构没有任何能力来捕获这些属性。 支持自定义类型的第三种方法是不使用静态XSD描述语法,而是使用生成的XSD。 可以根据文档中Log4j 2.x组件的描述来手写这样的XSD,但是更好的方法可能是利用Log4j 2.x中使用的@PluginFactory , @PluginElement和@PluginAttribute注释。源代码。 接下来的两个代码清单来自Apache Log4j 2.6.2代码库,并演示了这些注释如何描述给定类型的元素和属性。

ConsoleAppender.createAppender()签名

@PluginFactory
public static ConsoleAppender createAppender(@PluginElement("Layout") Layout layout,@PluginElement("Filter") final Filter filter,@PluginAttribute(value = "target", defaultString = "SYSTEM_OUT") final String targetStr,@PluginAttribute("name") final String name,@PluginAttribute(value = "follow", defaultBoolean = false) final String follow,@PluginAttribute(value = "ignoreExceptions", defaultBoolean = true) final String ignore)

SysLogAppender.createAppender()签名

@PluginFactory
public static SyslogAppender createAppender(// @formatter:off@PluginAttribute("host") final String host,@PluginAttribute(value = "port", defaultInt = 0) final int port,@PluginAttribute("protocol") final String protocolStr,@PluginElement("SSL") final SslConfiguration sslConfig,@PluginAttribute(value = "connectTimeoutMillis", defaultInt = 0) final int connectTimeoutMillis,@PluginAliases("reconnectionDelay") // deprecated@PluginAttribute(value = "reconnectionDelayMillis", defaultInt = 0) final int reconnectionDelayMillis,@PluginAttribute(value = "immediateFail", defaultBoolean = true) final boolean immediateFail,@PluginAttribute("name") final String name,@PluginAttribute(value = "immediateFlush", defaultBoolean = true) final boolean immediateFlush,@PluginAttribute(value = "ignoreExceptions", defaultBoolean = true) final boolean ignoreExceptions,@PluginAttribute(value = "facility", defaultString = "LOCAL0") final Facility facility,@PluginAttribute("id") final String id,@PluginAttribute(value = "enterpriseNumber", defaultInt = Rfc5424Layout.DEFAULT_ENTERPRISE_NUMBER) final int enterpriseNumber,@PluginAttribute(value = "includeMdc", defaultBoolean = true) final boolean includeMdc,@PluginAttribute("mdcId") final String mdcId,@PluginAttribute("mdcPrefix") final String mdcPrefix,@PluginAttribute("eventPrefix") final String eventPrefix,@PluginAttribute(value = "newLine", defaultBoolean = false) final boolean newLine,@PluginAttribute("newLineEscape") final String escapeNL,@PluginAttribute("appName") final String appName,@PluginAttribute("messageId") final String msgId,@PluginAttribute("mdcExcludes") final String excludes,@PluginAttribute("mdcIncludes") final String includes,@PluginAttribute("mdcRequired") final String required,@PluginAttribute("format") final String format,@PluginElement("Filter") final Filter filter,@PluginConfiguration final Configuration config,@PluginAttribute(value = "charset", defaultString = "UTF-8") final Charset charsetName,@PluginAttribute("exceptionPattern") final String exceptionPattern,@PluginElement("LoggerFields") final LoggerFields[] loggerFields, @PluginAttribute(value = "advertise", defaultBoolean = false) final boolean advertise)

这种方法需要几个步骤,因为一个人需要使用Log4j 2.x体系结构的主要组成部分的知识以及注释处理来动态生成XSD,然后使用JAXB生成能够封送综合Log4j 2.x的Java类。 XML。

要考虑的另一种选择是使用“简洁的” XML或另一种形式的Log4j 2.x配置 (例如JSON或属性文件 ),而不使用XSD生成用于编组Log4j 2.x配置的JAXB对象。 值得注意的是,用于Log4j 2.x且具有“ strict”格式的XML配置文件显然不需要针对Log4j-config.xsd进行验证,否则XML的“ strict”形式将无法完全指定Log4j2组态。 这意味着即使拥有XSD,剩下的价值还是供我们自己的工具或脚本使用,以便在与Log4j 2.x结合使用之前先使用它来验证我们的XML配置,或者用于编组/解编Log4j2.x。带有JAXB的XML。

结论

Log4j2发行版随附的Log4j-config.xsd不足以验证“严格” XML配置中的所有Log4j 2.x构造,同样不足以生成用于封送Log4j2严格XML的JAXB对象。 希望使用XSD进行验证或JAXB类生成的开发人员将需要手动更改XSD或从Log4j2源代码生成XSD。

这些参考文献已在上面的文章中链接到内联,但此处出于强调目的而列出。

  • 在Log4j2中,如何将XML模式与log4j2.xml关联?
  • [LOG4J2-170] Log4J-V2.0.xsd发生架构验证失败
  • [LOG4J2-411] 对链接到配置文件的XSD / DTD的支持
  • logging- log4j- 用户邮件列表 :“ Log4j2 Appender属性具有严格的xml配置 ”
    • 从注释生成XSD?

翻译自: https://www.javacodegeeks.com/2016/08/log4j-2-x-xsd-not-fully-descriptive.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/353836.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Protobuf学习笔记

Protobuf学习笔记 Posted by iamxhuon 2012/05/22 Leave a comment (0)Go to commentsProtocol buffers是什么&#xff1f; 首先了解一下Protocol Buffers(简称ProtoBuf)是什么&#xff1f;官网对它的定义如下&#xff1a; Protocol buffers are Google’s language-neutral, …

如何掌握Java内存(并保存程序)

通过AppDynamics解决应用程序问题的速度提高了10倍–以最小的开销在代码级深度监视生产应用程序。 开始免费试用&#xff01; 您花了无数小时来研究Java应用程序中的错误并在需要的地方获得其性能。 在测试期间&#xff0c;您注意到应用程序随着时间的推移逐渐变慢&#xff0c…

程序集版本号

程序集版本号分为4段&#xff0c;例如1.0.4.23。 第一段为主版本号&#xff0c;项目一但启动则不会更改。 第二段为次版本号&#xff0c;在项目功能做较大调整时增加&#xff0c;增量为1。 第三段为修订版本号&#xff0c;通常在解决缺陷或者细微功能变化时增加&#xff0c;增量…

py-kms使用方法

搭建py-kms服务器,先下载py-kms https://github.com/myanaloglife/py-kms 启动py-kms服务(需要服务器安装有python): python server.py 这样py-kms服务就启动好了,如果需要后台运行可以制作deamon脚本。 py-kms可以激活企业/专业版vl windows系统和vol版本的office软件: window…

JAVA泛型--待续

原做法&#xff1a; Map m new HashMap();m.put("key", "blarg");String s (String) m.get("key"); 泛型做法&#xff1a; Map<K,V> m new HashMap()<K,V>;m.put("key", "blarg");//非<K,V>类型无法操…

Tortoise SVN 版本控制常用操作知识

Tortoise SVN 版本控制常用操作知识 Posted on 2010-11-26 23:07 szh114 阅读(5897) 评论(0) 编辑 收藏 今天老大跑过来问我如何把SVN服务器上的当前版本回退到某一个版本上去&#xff0c;我没回答上来&#xff0c;很失败&#xff0c;所以现在整理一下Tortoise SVN的操作知识&…

如何导入任何JBoss BRMS示例项目

在过去几周内&#xff0c;JBoss BRMS演示的用户反复询问我以下内容时&#xff0c;会给您这些提示和技巧&#xff1a; “如何将与各种JBoss BRMS演示项目相关的项目导入到我自己的现有安装中&#xff1f;” 这意味着用户希望在产品的个人安装中有一个示例项目&#xff0c;而无…

2110: 扫雷

http://acm.zcmu.edu.cn/JudgeOnline/problem.php?id2110 2110: 扫雷 Time Limit: 1 Sec Memory Limit: 128 MBSubmit: 88 Solved: 36[Submit][Status][Web Board]Description 扫雷游戏你一定玩过吧&#xff01;现在给你若干个nm的地雷阵&#xff0c;请你计算出每个矩阵中每…

使用eclipse生成文档(javadoc)

使用eclipse生成文档&#xff08;javadoc&#xff09;主要有三种方法&#xff1a; 1&#xff0c;在项目列表中按右键&#xff0c;选择Export&#xff08;导出&#xff09;&#xff0c;然后在Export(导出)对话框中选择java下的javadoc&#xff0c;提交到下一步。 在Javadoc Gene…

青椒苗

转载于:https://www.cnblogs.com/wainiwann/p/8793418.html

更改日志级别_如何在运行时更改日志记录级别

更改日志级别在运行时中更改日志记录级别非常重要&#xff0c;这主要在生产环境中非常重要&#xff0c;在生产环境中&#xff0c;您可能希望在有限的时间内进行调试日志记录。 好了&#xff0c;更改根记录器非常简单–假设您有一个具有所需记录级别的输入参数&#xff0c;只需…

JDBC和Ibatis中的Date,Time,Timestamp处理

JDBC和Ibatis中的Date,Time,Timestamp处理 November 25th, 2010西坪 Leave a commentGo to comments在此前&#xff0c;遇到过使用Ibatis操作Oracle时时间精度丢失的问题&#xff0c;昨天又遇到JDBC操作MySQL时间字段的问题&#xff0c;从网上看到各种式样的解释这些问题的博文…

每日算法之抽签

X星球要派出一个5人组成的观察团前往W星。其中&#xff1a;A国最多可以派出4人。B国最多可以派出2人。C国最多可以派出2人。....那么最终派往W星的观察团会有多少种国别的不同组合呢&#xff1f;下面的程序解决了这个问题。数组a[] 中既是每个国家可以派出的最多的名额。程序执…

如何开始Java机器学习

什么是开始使用Java机器学习的最佳工具&#xff1f; 他们已经存在了一段时间&#xff0c;但如今看来&#xff0c;每个人都在谈论人工智能和机器学习。 对于科学家和研究人员而言&#xff0c;它已不再是秘密&#xff0c;几乎可以在任何新兴技术中实现。 在下面的文章中&#x…

keil中关于使用_at_绝对地址定位问题

keil中关于使用_at_绝对地址定位问题 2008-01-07 13:46:26| 分类&#xff1a; MCU51 | 标签&#xff1a; |字号大中小 订阅 在网上看到有人提到在keil中使用_at_进行绝对地址定位问题&#xff0c;我简单介绍一下它的用法。 使用_at_关键字对存储器进行绝对地址定位程序…

ztree树

常规的ztree树 后台数据封装成list对象 public PageModel getTreeBuildingRegData(Map<String, String> params) {PageModel pageModelnew PageModel();String statusparams.get("status");String orgIdparams.get("org_id");List<OmsBuildingReg…

如何提高效率

如何提高效率 时间管理 April 28th, 2011 本文来自读者 桃雨 翻译投稿。 Aaron Swartz写过一篇很有名的文章&#xff0c;叫做《HOWTO: Be more productive》&#xff08;如何提高效率&#xff09;。这篇文章写的实在是太好了&#xff0c;我看了好多遍&#xff0c;很赞同作者的…

Andrew Ng - 深度学习工程师 - Part 2. 改善深层神经网络:超参数调试、正则化以及优化(Week 1. 机器学习的实用层面)...

第1周 机器学习的实用层面 1.1 训练/开发/测试 早期机器学习时代&#xff08;数据规模较小&#xff09;&#xff0c;如果不需要dev set&#xff0c;常见的划分有 70%/30% 的训练/测试 划分&#xff0c;如果需要验证集&#xff0c;常见的是 60%/20%/20%划分 在big data era&…

jms 如何测试_使用JMSTester对JMS层进行基准测试

jms 如何测试对于我去过的大多数客户端&#xff0c;使用ActiveMQ扩展JMS消息传递层是一个优先事项。 有多种方法可以实现这一目标&#xff0c;但毫无疑问&#xff0c;创建基准并分析实际硬件上的体系结构&#xff08;或者正如我的同事Gary Tully所说的“询问机器”&#xff09;…

为什么待办事项清单不管用

为什么待办事项清单不管用 时间管理 November 22nd, 2012 本文原文来自 Harvard Business Review&#xff0c;由 换装迷宫tayy 翻译。 停止制作你的待办事项清单吧。它们只会让你感觉失败和受挫。想想你正在管理的那些待办清单&#xff1a;有多少事项从年初起就已经在那儿了&…