Skip to content
Advertisement

How to configure slf4j (for JDA) to work with log4j (for Minecraft Paper)?

I’m making plugin for Minecraft – ‘Paper‘ exactly. And it uses JDA for Discord bot function.

The problem is, Minecraft(Paper) uses log4j as its logging library. JDA uses slf4j as its logging library. I want JDA to use log4j so that error message of JDA would be shown in console as plugin’s error message. (See EDIT2 for actual logs)

No System.out.println() because Minecraft(Paper) will complain about using it.
No Logback because I think it is another logging library, thus it cannot work well with Minecraft(Paper)’s logging system (no JDA logs in Minecraft log etc.). I don’t want to implement another logging library when there is already logging system provided by Minecraft, which is log4j.

JDA wiki only describes about Logback so I have to find my own way for making JDA with Minecraft’s logging system, but it was no success.

For example:

// Something went wrong in JDA and shows stacktrace
[05:20:26] [Server thread/ERROR]: [MyPlugin] [JDA] 'JDA Error Message'
(prints stacktrace of the error)

// Show debug message of WebSocketClient (Since it is debug message, this can be turned off)
[05:20:26] [Server thread/DEBUG]: [MyPlugin] [JDA] WebSocketClient - Connected to WebSocket

// Show JDA message when JDA bot is loaded
[05:20:26] [Server thread/DEBUG]: [MyPlugin] [JDA] JDA - Finished Loading!

These all messages should be part of the Minecraft(Paper)’s logging system, not mimicing it. This means, it should use JavaPlugin#getLogger().info() or something like this in somewhere of the code.

How to make JDA to be like this?
Just implementing log4j-slf4j18-impl doesn’t work. I think I should do something about JDA’s logging stuff.


EDIT: Here is current build.gradle file content. LINK

Currently, my plugin implements log4j-slf4j-impl for JDA.

Advertisement

Answer

You need to add a “bridge” from slf4j to log4j. The appropriate dependency needs to fit both the slf4j version and the log4j version.

To find the correct version I checked the build.gradle.kts of JDA JDA uses the 1.7.25 version of slf4j and your module uses the 2.17.2 version of the log4j.

So you need to add log4j-slf4j-impl.
The log4j-slf4j18-impl is for sl4j from 18 and newer version.

Maven Version

<dependency>
  <groupId>org.apache.logging.log4j</groupId>
  <artifactId>log4j-slf4j-impl</artifactId>
  <version>2.17.2</version>
</dependency>

Gradle Version

compile 'org.apache.logging.log4j:log4j-slf4j-impl:2.17.2'

Also, making the assumption that your build depends on the JDA, it might be helpful to completely omit importing the SL4J since depending on JDA will make the SL4J available to your plugin. JDA dependency on SLF4J is declared as an API and therefore is available.

This was also derived from the build.gradle.kts of JDA

So most likely you can safely remove org.slf4j:slf4j-api:1.8.0-beta4 from your dependencies.

Update: for the gradle.build file.

  • Shadowjar-ing/shading sl4j and log4j might interfere with the initialization process. I could find an occurrence to support this. You could remove all related relocations and try again.
  • Replace compileOnly('org.slf4j:slf4j-api:1.7.36') with compileOnly('org.slf4j:slf4j-api:1.7.25') to match the version that JDA declares. Most probably this has nothing to do with the error faced.
7 People found this is helpful
Advertisement