-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Improve LoggerUtils support and add TestLoggerExtension (#3123)
This commit improves `LoggerUtils` and adds supporting JUnit5 extension and annotations in reactor-core tests: `LoggerUtils` now has support to _redirect_ rather than _copy/capture_ log messages when the logger factory is installed early. In reactor-core tests, a `TestLoggerExtension` is added that sets up a `TestLogger` and activates capture/redirection via `LoggerUtils`: - before the test, it creates a `TestLogger` (configured depending on test annotations) and sets up `LoggerUtils` with said `TestLogger` - as a `ParameterResolver` it injects the `TestLogger` into the test - after the test it `disableCapture()` The Extension should be applied to individual tests. Convenience annotations are provided that fine tune the `TestLogger` that will be injected: - `@Capture` when the loggers should capture log output, ie. go both to original logger and TestLogger - `@Redirect` when the loggers should redirect log output, ie. only go to TestLogger This commit further simplifies the `LoggerUtils` internals, putting more state into the `CapturingFactory` rather than as a top level static field. Finally, it adds a ton of test coverage to both `TestLogger` and `LoggerUtils`.
- Loading branch information
1 parent
41e956d
commit 6a89d1f
Showing
18 changed files
with
1,183 additions
and
772 deletions.
There are no files selected for viewing
98 changes: 98 additions & 0 deletions
98
reactor-core/src/test/java/reactor/core/TestLoggerExtension.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,98 @@ | ||
/* | ||
* Copyright (c) 2022 VMware Inc. or its affiliates, All Rights Reserved. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* https://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
package reactor.core; | ||
|
||
import java.lang.annotation.ElementType; | ||
import java.lang.annotation.Retention; | ||
import java.lang.annotation.RetentionPolicy; | ||
import java.lang.annotation.Target; | ||
|
||
import org.junit.jupiter.api.extension.AfterEachCallback; | ||
import org.junit.jupiter.api.extension.BeforeEachCallback; | ||
import org.junit.jupiter.api.extension.ExtendWith; | ||
import org.junit.jupiter.api.extension.ExtensionContext; | ||
import org.junit.jupiter.api.extension.ParameterContext; | ||
import org.junit.jupiter.api.extension.ParameterResolutionException; | ||
import org.junit.jupiter.api.extension.ParameterResolver; | ||
|
||
import reactor.test.util.LoggerUtils; | ||
import reactor.test.util.TestLogger; | ||
import reactor.util.Logger; | ||
import reactor.util.annotation.Nullable; | ||
|
||
/** | ||
* A JUnit5 extension that installs a {@link TestLogger} as the capturing instance via {@link LoggerUtils#enableCaptureWith(Logger)}, | ||
* {@link LoggerUtils#disableCapture() disable capture} at the end of the test and injects the {@link TestLogger} | ||
* into the test case (by implementing {@link ParameterResolver}). | ||
* | ||
* @author Simon Baslé | ||
*/ | ||
public class TestLoggerExtension implements ParameterResolver, AfterEachCallback, BeforeEachCallback { | ||
|
||
/** | ||
* Set up a default {@link TestLoggerExtension}, unless @{@link Redirect} annotation is also present. | ||
* By default loggers will route the log messages to both the original logger and the injected | ||
* {@link TestLogger}, and in the latter there won't be automatic inclusion of thread names. | ||
* | ||
* @see Redirect | ||
*/ | ||
@Retention(RetentionPolicy.RUNTIME) | ||
@Target({ ElementType.TYPE, ElementType.METHOD }) | ||
@ExtendWith(TestLoggerExtension.class) | ||
public @interface Capture { } | ||
|
||
/** | ||
* Set up a {@link TestLoggerExtension} that routes log messages only to the injected {@link TestLogger}, | ||
* suppressing the logs from the original logger. Messages don't include thread names. | ||
*/ | ||
@Retention(RetentionPolicy.RUNTIME) | ||
@Target({ ElementType.TYPE, ElementType.METHOD }) | ||
@ExtendWith(TestLoggerExtension.class) | ||
public @interface Redirect { } | ||
|
||
TestLogger logger; | ||
|
||
@Override | ||
public void beforeEach(ExtensionContext context) throws Exception { | ||
if (context.getElement().isPresent()) { | ||
boolean suppressOriginal = context.getElement().get().isAnnotationPresent(Redirect.class); | ||
this.logger = new TestLogger(false); | ||
LoggerUtils.enableCaptureWith(logger, !suppressOriginal); | ||
} | ||
} | ||
|
||
@Override | ||
public void afterEach(ExtensionContext context) throws Exception { | ||
LoggerUtils.disableCapture(); | ||
} | ||
|
||
@Override | ||
public boolean supportsParameter(ParameterContext parameterContext, ExtensionContext extensionContext) | ||
throws ParameterResolutionException { | ||
return parameterContext.getParameter().getType() == TestLogger.class; | ||
} | ||
|
||
@Override | ||
@Nullable | ||
public Object resolveParameter(ParameterContext parameterContext, ExtensionContext extensionContext) | ||
throws ParameterResolutionException { | ||
if (parameterContext.getParameter().getType() == TestLogger.class) { | ||
return this.logger; | ||
} | ||
return null; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.