You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@logging.apache.org by Remko Popma <re...@gmail.com> on 2017/06/28 13:43:35 UTC
Re: [1/2] logging-log4j2 git commit: LOG4J2-1958 Deprecate
SerializedLayout and remove it as default
In the manual pages, can we mention that in previous versions the default
was SerializedLayout, but as of log4j-2.9 users need to explicitly specify
a layout since there is no default? I think it is important to document the
log4j version when this change took place.
On Wed, Jun 28, 2017 at 9:52 PM, <mi...@apache.org> wrote:
> Repository: logging-log4j2
> Updated Branches:
> refs/heads/LOG4J2-1958 [created] c1b90f961
>
>
> LOG4J2-1958 Deprecate SerializedLayout and remove it as default
>
>
> Project: http://git-wip-us.apache.org/repos/asf/logging-log4j2/repo
> Commit: http://git-wip-us.apache.org/repos/asf/logging-log4j2/
> commit/330a16f9
> Tree: http://git-wip-us.apache.org/repos/asf/logging-log4j2/tree/330a16f9
> Diff: http://git-wip-us.apache.org/repos/asf/logging-log4j2/diff/330a16f9
>
> Branch: refs/heads/LOG4J2-1958
> Commit: 330a16f923a8eb34b983cc3fb255927dd9699323
> Parents: 3f45368
> Author: Mikael Ståldal <mi...@staldal.nu>
> Authored: Wed Jun 28 14:50:52 2017 +0200
> Committer: Mikael Ståldal <mi...@staldal.nu>
> Committed: Wed Jun 28 14:50:52 2017 +0200
>
> ----------------------------------------------------------------------
> .../log4j/core/appender/SocketAppender.java | 8 +++---
> .../log4j/core/appender/mom/JmsAppender.java | 7 +++--
> .../log4j/core/layout/SerializedLayout.java | 6 +++++
> .../log4j/core/appender/SocketAppenderTest.java | 28 ++++++++++++++------
> src/changes/changes.xml | 3 +++
> src/site/xdoc/manual/appenders.xml | 15 ++++++-----
> src/site/xdoc/manual/layouts.xml.vm | 9 +++++--
> src/site/xdoc/manual/migration.xml | 2 +-
> 8 files changed, 54 insertions(+), 24 deletions(-)
> ----------------------------------------------------------------------
>
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/log4j-core/src/main/java/org/apache/logging/log4j/
> core/appender/SocketAppender.java
> ----------------------------------------------------------------------
> diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/SocketAppender.java
> b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/SocketAppender.java
> index 8c2b83d..b433403 100644
> --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/SocketAppender.java
> +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/SocketAppender.java
> @@ -36,7 +36,6 @@ import org.apache.logging.log4j.core.
> config.plugins.PluginElement;
> import org.apache.logging.log4j.core.config.plugins.PluginFactory;
> import org.apache.logging.log4j.core.config.plugins.validation.
> constraints.ValidHost;
> import org.apache.logging.log4j.core.config.plugins.validation.
> constraints.ValidPort;
> -import org.apache.logging.log4j.core.layout.SerializedLayout;
> import org.apache.logging.log4j.core.net.AbstractSocketManager;
> import org.apache.logging.log4j.core.net.Advertiser;
> import org.apache.logging.log4j.core.net.DatagramSocketManager;
> @@ -197,7 +196,8 @@ public class SocketAppender extends
> AbstractOutputStreamAppender<AbstractSocketM
> final boolean bufferedIo = isBufferedIo();
> Layout<? extends Serializable> layout = getLayout();
> if (layout == null) {
> - layout = SerializedLayout.createLayout();
> + AbstractLifeCycle.LOGGER.error("No layout provided for
> SocketAppender");
> + return null;
> }
>
> final String name = getName();
> @@ -280,7 +280,7 @@ public class SocketAppender extends
> AbstractOutputStreamAppender<AbstractSocketM
> * If {@code "true"} (default) exceptions encountered when
> appending events are logged; otherwise they
> * are propagated to the caller.
> * @param layout
> - * The layout to use (defaults to SerializedLayout).
> + * The layout to use. Required, there is no default.
> * @param filter
> * The Filter or null.
> * @param advertise
> @@ -354,7 +354,7 @@ public class SocketAppender extends
> AbstractOutputStreamAppender<AbstractSocketM
> * If {@code "true"} (default) exceptions encountered when
> appending events are logged; otherwise they
> * are propagated to the caller.
> * @param layout
> - * The layout to use (defaults to {@link
> SerializedLayout}).
> + * The layout to use. Required, there is no default.
> * @param filter
> * The Filter or null.
> * @param advertise
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/log4j-core/src/main/java/org/apache/logging/log4j/
> core/appender/mom/JmsAppender.java
> ----------------------------------------------------------------------
> diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/mom/JmsAppender.java
> b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/mom/JmsAppender.java
> index 84b88fa..906b36f 100644
> --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/mom/JmsAppender.java
> +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> appender/mom/JmsAppender.java
> @@ -39,7 +39,6 @@ import org.apache.logging.log4j.core.config.plugins.
> PluginBuilderAttribute;
> import org.apache.logging.log4j.core.config.plugins.PluginBuilderFactory;
> import org.apache.logging.log4j.core.config.plugins.PluginElement;
> import org.apache.logging.log4j.core.config.plugins.validation.
> constraints.Required;
> -import org.apache.logging.log4j.core.layout.SerializedLayout;
> import org.apache.logging.log4j.core.net.JndiManager;
> import org.apache.logging.log4j.status.StatusLogger;
>
> @@ -88,7 +87,7 @@ public class JmsAppender extends AbstractAppender {
> private char[] password;
>
> @PluginElement("Layout")
> - private Layout<? extends Serializable> layout =
> SerializedLayout.createLayout();
> + private Layout<? extends Serializable> layout;
>
> @PluginElement("Filter")
> private Filter filter;
> @@ -128,6 +127,10 @@ public class JmsAppender extends AbstractAppender {
> // JmsManagerFactory has already logged an ERROR.
> return null;
> }
> + if (layout == null) {
> + LOGGER.error("No layout provided for JmsAppender");
> + return null;
> + }
> return new JmsAppender(name, filter, layout,
> ignoreExceptions, reconnectOnExceptionMessages,
> reconnectAttempts, reconnectIntervalMillis,
> actualJmsManager);
> }
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/log4j-core/src/main/java/org/apache/logging/log4j/
> core/layout/SerializedLayout.java
> ----------------------------------------------------------------------
> diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/layout/SerializedLayout.java
> b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> layout/SerializedLayout.java
> index 04b52e8..43700e0 100644
> --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/
> layout/SerializedLayout.java
> +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/
> layout/SerializedLayout.java
> @@ -29,7 +29,11 @@ import org.apache.logging.log4j.core.
> config.plugins.PluginFactory;
>
> /**
> * Formats a {@link LogEvent} in its Java serialized form.
> + *
> + * @deprecated Java Serialization has inherent security weaknesses, using
> this layout is no longer recommended.
> + * An alternative layout containing the same information is {@link
> JsonLayout} when configured with properties="true".
> */
> +@Deprecated
> @Plugin(name = "SerializedLayout", category = Node.CATEGORY, elementType
> = Layout.ELEMENT_TYPE, printObject = true)
> public final class SerializedLayout extends AbstractLayout<LogEvent> {
>
> @@ -47,6 +51,7 @@ public final class SerializedLayout extends
> AbstractLayout<LogEvent> {
>
> private SerializedLayout() {
> super(null, null, null);
> + LOGGER.warn("SerializedLayout is deprecated due to the inherent
> security weakness in Java Serialization. Consider using another layout,
> e.g. JsonLayout");
> }
>
> /**
> @@ -82,6 +87,7 @@ public final class SerializedLayout extends
> AbstractLayout<LogEvent> {
> * Creates a SerializedLayout.
> * @return A SerializedLayout.
> */
> + @Deprecated
> @PluginFactory
> public static SerializedLayout createLayout() {
> return new SerializedLayout();
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/
> SocketAppenderTest.java
> ----------------------------------------------------------------------
> diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/
> appender/SocketAppenderTest.java b/log4j-core/src/test/java/
> org/apache/logging/log4j/core/appender/SocketAppenderTest.java
> index 64a29ae..b02ef76 100644
> --- a/log4j-core/src/test/java/org/apache/logging/log4j/core/
> appender/SocketAppenderTest.java
> +++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/
> appender/SocketAppenderTest.java
> @@ -21,10 +21,9 @@ import static org.junit.Assert.assertNotNull;
> import static org.junit.Assert.assertTrue;
> import static org.junit.Assert.fail;
>
> -import java.io.ByteArrayInputStream;
> import java.io.EOFException;
> import java.io.IOException;
> -import java.io.ObjectInputStream;
> +import java.io.InputStream;
> import java.net.DatagramPacket;
> import java.net.DatagramSocket;
> import java.net.ServerSocket;
> @@ -36,6 +35,8 @@ import java.util.concurrent.BlockingQueue;
> import java.util.concurrent.CountDownLatch;
> import java.util.concurrent.TimeUnit;
>
> +import com.fasterxml.jackson.databind.MappingIterator;
> +import com.fasterxml.jackson.databind.ObjectMapper;
> import org.apache.logging.log4j.Level;
> import org.apache.logging.log4j.LoggingException;
> import org.apache.logging.log4j.ThreadContext;
> @@ -43,6 +44,9 @@ import org.apache.logging.log4j.core.Appender;
> import org.apache.logging.log4j.core.LogEvent;
> import org.apache.logging.log4j.core.Logger;
> import org.apache.logging.log4j.core.LoggerContext;
> +import org.apache.logging.log4j.core.impl.Log4jLogEvent;
> +import org.apache.logging.log4j.core.jackson.Log4jJsonObjectMapper;
> +import org.apache.logging.log4j.core.layout.JsonLayout;
> import org.apache.logging.log4j.core.net.Protocol;
> import org.apache.logging.log4j.core.util.Constants;
> import org.apache.logging.log4j.core.util.Throwables;
> @@ -128,6 +132,7 @@ public class SocketAppenderTest {
> .withName("test")
> .withImmediateFail(false)
> .withBufferSize(bufferSize)
> + .withLayout(JsonLayout.newBuilder().setProperties(
> true).build())
> .build();
> // @formatter:on
> appender.start();
> @@ -174,6 +179,7 @@ public class SocketAppenderTest {
> .withReconnectDelayMillis(-1)
> .withName("test")
> .withImmediateFail(false)
> + .withLayout(JsonLayout.newBuilder().setProperties(
> true).build())
> .build();
> // @formatter:on
> assertNotNull(appender);
> @@ -195,6 +201,7 @@ public class SocketAppenderTest {
> .withReconnectDelayMillis(-1)
> .withName("test")
> .withImmediateFail(false)
> + .withLayout(JsonLayout.newBuilder().setProperties(
> true).build())
> .build();
> // @formatter:on
> appender.start();
> @@ -220,6 +227,7 @@ public class SocketAppenderTest {
> .withReconnectDelayMillis(100)
> .withName("test")
> .withImmediateFail(false)
> + .withLayout(JsonLayout.newBuilder().setProperties(
> true).build())
> .build();
> // @formatter:on
> appender.start();
> @@ -251,6 +259,7 @@ public class SocketAppenderTest {
> .withName("test")
> .withImmediateFail(false)
> .withIgnoreExceptions(false)
> + .withLayout(JsonLayout.newBuilder().setProperties(
> true).build())
> .build();
> // @formatter:on
> appender.start();
> @@ -277,6 +286,7 @@ public class SocketAppenderTest {
> private final CountDownLatch latch = new CountDownLatch(1);
> private volatile int count = 0;
> private final BlockingQueue<LogEvent> queue;
> + private final ObjectMapper objectMapper = new
> Log4jJsonObjectMapper();
>
> public UdpSocketTestServer() throws IOException {
> this.sock = new DatagramSocket(PORT);
> @@ -302,10 +312,8 @@ public class SocketAppenderTest {
> while (!shutdown) {
> latch.countDown();
> sock.receive(packet);
> - final ObjectInputStream ois = new
> ObjectInputStream(new ByteArrayInputStream(packet.getData()));
> ++count;
> - final Object received = ois.readObject(); // separate
> lines for debugging
> - final LogEvent event = (LogEvent) received;
> + final LogEvent event = objectMapper.readValue(packet.getData(),
> Log4jLogEvent.class);
> queue.add(event);
> }
> } catch (final Throwable e) {
> @@ -331,6 +339,7 @@ public class SocketAppenderTest {
> private volatile boolean shutdown = false;
> private volatile int count = 0;
> private final BlockingQueue<LogEvent> queue;
> + private final ObjectMapper objectMapper = new
> Log4jJsonObjectMapper();
>
> @SuppressWarnings("resource")
> public TcpSocketTestServer(final int port) throws IOException {
> @@ -361,10 +370,13 @@ public class SocketAppenderTest {
> try {
> try (final Socket socket = serverSocket.accept()) {
> if (socket != null) {
> - final ObjectInputStream ois = new
> ObjectInputStream(socket.getInputStream());
> + final InputStream is = socket.getInputStream();
> while (!shutdown) {
> - queue.add((LogEvent) ois.readObject());
> - ++count;
> + final MappingIterator<LogEvent>
> mappingIterator = objectMapper.readerFor(Log4jLogEvent.class).
> readValues(is);
> + while (mappingIterator.hasNextValue()) {
> + queue.add(mappingIterator.nextValue());
> + ++count;
> + }
> }
> }
> }
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/src/changes/changes.xml
> ----------------------------------------------------------------------
> diff --git a/src/changes/changes.xml b/src/changes/changes.xml
> index 91b1101..a171173 100644
> --- a/src/changes/changes.xml
> +++ b/src/changes/changes.xml
> @@ -31,6 +31,9 @@
> - "remove" - Removed
> -->
> <release version="2.9.0" date="2017-MM-DD" description="GA Release
> 2.9.0">
> + <action issue="LOG4J2-1958" dev="mikes" type="update">
> + Deprecate SerializedLayout and remove it as default.
> + </action>
> <action issue="LOG4J2-1950" dev="ggregory" type="update"
> due-to="Pierrick HYMBERT">
> Fix docker build with jdk9 requirements (#84).
> </action>
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/src/site/xdoc/manual/appenders.xml
> ----------------------------------------------------------------------
> diff --git a/src/site/xdoc/manual/appenders.xml b/src/site/xdoc/manual/
> appenders.xml
> index ba1bf7d..bbb4c5f 100644
> --- a/src/site/xdoc/manual/appenders.xml
> +++ b/src/site/xdoc/manual/appenders.xml
> @@ -1295,8 +1295,7 @@ public class ConnectionFactory {
> <td>layout</td>
> <td>Layout</td>
> <td>
> - The Layout to use to format the LogEvent. If you do not
> specify a layout,
> - this appender will use a <a href="layouts.html#
> SerializedLayout">SerializedLayout</a>.
> + The Layout to use to format the LogEvent. Required, there
> is no default.
> </td>
> </tr>
> <tr>
> @@ -1372,7 +1371,9 @@ public class ConnectionFactory {
> <Configuration status="warn" name="MyApp">
> <Appenders>
> <JMS name="jmsQueue" destinationBindingName="MyQueue"
> - factoryBindingName="MyQueueConnectionFactory"/>
> + factoryBindingName="MyQueueConnectionFactory">
> + <JsonLayout properties="true"/>
> + </JMS>
> </Appenders>
> <Loggers>
> <Root level="error">
> @@ -4302,7 +4303,7 @@ public class JpaLogEntity extends
> AbstractLogEventWrapperEntity {
> <p>
> The <code>SocketAppender</code> is an OutputStreamAppender
> that writes its output to a remote destination
> specified by a host and port. The data can be sent over
> either TCP or UDP and can be sent in any format.
> - The default format is to send a Serialized LogEvent. You can
> optionally secure communication with SSL.
> + You can optionally secure communication with SSL.
> </p>
> <table>
> <caption align="top"><code>SocketAppender</code>
> Parameters</caption>
> @@ -4369,7 +4370,7 @@ public class JpaLogEntity extends
> AbstractLogEventWrapperEntity {
> <tr>
> <td>layout</td>
> <td>Layout</td>
> - <td>The Layout to use to format the LogEvent. The default
> is SerializedLayout.</td>
> + <td>The Layout to use to format the LogEvent. Required,
> there is no default.</td>
> </tr>
> <tr>
> <td>reconnectionDelayMillis</td>
> @@ -4402,7 +4403,7 @@ public class JpaLogEntity extends
> AbstractLogEventWrapperEntity {
> <Configuration status="warn" name="MyApp" packages="">
> <Appenders>
> <Socket name="socket" host="localhost" port="9500">
> - <SerializedLayout />
> + <JsonLayout properties="true"/>
> </Socket>
> </Appenders>
> <Loggers>
> @@ -4419,7 +4420,7 @@ public class JpaLogEntity extends
> AbstractLogEventWrapperEntity {
> <Configuration status="warn" name="MyApp" packages="">
> <Appenders>
> <Socket name="socket" host="localhost" port="9500">
> - <SerializedLayout />
> + <JsonLayout properties="true"/>
> <SSL>
> <KeyStore location="log4j2-keystore.jks" password="changeme"/>
> <TrustStore location="truststore.jks" password="changeme"/>
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/src/site/xdoc/manual/layouts.xml.vm
> ----------------------------------------------------------------------
> diff --git a/src/site/xdoc/manual/layouts.xml.vm b/src/site/xdoc/manual/
> layouts.xml.vm
> index f65db0d..7d17fd1 100644
> --- a/src/site/xdoc/manual/layouts.xml.vm
> +++ b/src/site/xdoc/manual/layouts.xml.vm
> @@ -1974,8 +1974,13 @@ at org.apache.logging.log4j.core.
> pattern.ExtendedThrowableTest.testException(Ext
> </subsection>
> <a name="SerializedLayout"/>
> <subsection name="Serialized Layout">
> - <p>The SerializedLayout simply serializes the LogEvent into a
> byte array using Java Serialization. This is useful when
> - sending messages via JMS or via a Socket connection. The
> SerializedLayout accepts no parameters.
> + <p>The SerializedLayout simply serializes the LogEvent into a
> byte array using Java Serialization.
> + The SerializedLayout accepts no parameters.
> + </p>
> + <p>
> + Java Serialization has inherent security weaknesses, using this
> layout is no longer recommended.
> + An alternative layout containing the same information is <a
> href="#JSONLayout">JsonLayout</a>,
> + when configured with <code>properties="true"</code>.
> </p>
> </subsection>
> <a name="SyslogLayout"/>
>
> http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/
> 330a16f9/src/site/xdoc/manual/migration.xml
> ----------------------------------------------------------------------
> diff --git a/src/site/xdoc/manual/migration.xml b/src/site/xdoc/manual/
> migration.xml
> index e154f14..e503277 100644
> --- a/src/site/xdoc/manual/migration.xml
> +++ b/src/site/xdoc/manual/migration.xml
> @@ -240,7 +240,7 @@
> <Configuration>
> <Appenders>
> <Socket name="A1" host="localHost" port="5000">
> - <SerializedLayout/>
> + <PatternLayout pattern="%t %-5p %c{2} - %m%n"/>
> </Socket>
> <Console name="STDOUT" target="SYSTEM_OUT">
> <PatternLayout pattern="%d %-5p [%t] %C{2} (%F:%L) - %m%n"/>
>
>