捕获SpringBoot应用程序中某个包的@Sl4j输出。

huangapple go评论77阅读模式
英文:

Capture output of @Sl4j for a package in a SpringBoot application

问题

这是您要翻译的代码部分:

我有一个类它使用Flyway来为一个应用程序应用迁移

import lombok.extern.slf4j.Slf4j;
import org.flywaydb.core.Flyway;
import org.flywaydb.core.api.MigrationInfo;
import org.flywaydb.core.api.MigrationInfoService;
import org.flywaydb.core.api.MigrationVersion;
import org.flywaydb.core.api.configuration.FluentConfiguration;
import org.flywaydb.core.api.output.MigrateResult;
import org.flywaydb.core.internal.info.MigrationInfoDumper;

import java.util.Properties;

@Slf4j
public class FlywayService {

    Flyway flyway;

    public FlywayService(Properties props, String dbServer, String schema, String user, password) {
        FluentConfiguration flywayConfig = Flyway.configure();
        flywayConfig.configuration(props);

        flywayConfig.dataSource("jdbc:oracle:thin:@" + dbServer, user, password);
        flywayConfig.schemas(schema.toUpperCase());
        flyway = flywayConfig.load();
    }

    public void runInfo() {
        MigrationInfoService info = flyway.info();
        MigrationInfo current = info.current();
        MigrationVersion currentSchemaVersion = current == null ? MigrationVersion.EMPTY : current.getVersion();

        MigrationVersion schemaVersionToOutput = currentSchemaVersion == null ? MigrationVersion.EMPTY : currentSchemaVersion;
        StringBuffer buffer = new StringBuffer();
        buffer.append("Schema version: ")
                .append(schemaVersionToOutput).append("\n")
                .append(MigrationInfoDumper.dumpToAsciiTable(info.all()));

        log.info(buffer.toString());
    }
}

请注意,您提供的代码包含一些HTML转义字符(例如"),这些字符在代码中应该被删除。如果您要将这些代码放入Java文件中,需要删除这些HTML转义字符。

英文:

I have a class which is using Flyway to apply migrations for an application

import lombok.extern.slf4j.Slf4j;
import org.flywaydb.core.Flyway;
import org.flywaydb.core.api.MigrationInfo;
import org.flywaydb.core.api.MigrationInfoService;
import org.flywaydb.core.api.MigrationVersion;
import org.flywaydb.core.api.configuration.FluentConfiguration;
import org.flywaydb.core.api.output.MigrateResult;
import org.flywaydb.core.internal.info.MigrationInfoDumper;

import java.util.Properties;

@Slf4j
public class FlywayService {

    Flyway flyway;

    public FlywayService(Properties props, String dbServer, String schema, String user, String password) {
        FluentConfiguration flywayConfig = Flyway.configure();
        flywayConfig.configuration(props);

        flywayConfig.dataSource("jdbc:oracle:thin:@" + dbServer, user, password);
        flywayConfig.schemas(schema.toUpperCase());
        flyway = flywayConfig.load();
    }

    public void runInfo() {
        MigrationInfoService info = flyway.info();
        MigrationInfo current = info.current();
        MigrationVersion currentSchemaVersion = current == null ? MigrationVersion.EMPTY : current.getVersion();

        MigrationVersion schemaVersionToOutput = currentSchemaVersion == null ? MigrationVersion.EMPTY : currentSchemaVersion;
        StringBuffer buffer = new StringBuffer();
        buffer.append("Schema version: ")
                .append(schemaVersionToOutput).append("\n")
                .append(MigrationInfoDumper.dumpToAsciiTable(info.all()));

        log.info(buffer.toString());

    }
}

Logging is made through lombok(version 1.18.22) @Sl4j. What I need is to capture the all the log lines Flyway output to a String for some further processing but also keeping the lines logged by Flyway in spring.log.
捕获SpringBoot应用程序中某个包的@Sl4j输出。

Also, I'm running Flyway multithreaded as I'm applying migrations to several hundreds schemas.
Even I've searched for several hours, I still could not find an approach to do this.

答案1

得分: 1

代码部分不要翻译:

How about configuring all the flyway loggers (i.e. logger start with the name org.flywaydb) to output the logs to a file appender with a fixed file path , then your codes read all content from this log file to a variable for further processing ?

The file appender also need to be configured as additive such that it will forward the log to the original root logger which print the logs to console. It is also required to be configured as "non-append" mode which will clear the file before writing the logs to ensure that the log file will not contain the log from the previous run .

If you need to execute Flyway concurrently in multiple threads , you can use routing appender to forward the logs of different threads to their own separate log files based on some thread identifier you defined in MDC

An example configuration is :

<Appenders>
   <Routing name="Routing">
			<Routes pattern="$${ctx:threadId}">
				<Route>
					<File fileName="/logs/flyway-${ctx:threadId}.log"
							name="flyway-${ctx:threadId}"
							append="false">						
					</File>
				</Route>
			</Routes>
		</Routing>
</Appenders>


<Loggers>
   <Logger name="org.flywaydb" level="DEBUG" >
			<AppenderRef ref="Routing"/>
	</Logger>
</Loggers>

In codes before you execute flyway , you configure a thread identifier and put it in MDC , something likes :

String threadId = threadId +  UUID.randomUUID().toString();

ThreadContext.put("threadId", threadId);

//execute flyway

//read all content from log to a string to further process
Path logFilePath = Path.of("/logs/flyway-" + threadId + ".log");
String logs = Files.readString(logFilePath);

ThreadContext.clearAll();
英文:

How about configuring all the flyway loggers (i.e. logger start with the name org.flywaydb) to output the logs to a file appender with a fixed file path , then your codes read all content from this log file to a variable for further processing ?

The file appender also need to be configured as additive such that it will forward the log to the original root logger which print the logs to console. It is also required to be configured as "non-append" mode which will clear the file before writing the logs to ensure that the log file will not contain the log from the previous run .

If you need to execute Flyway concurrently in multiple threads , you can use routing appender to forward the logs of different threads to their own separate log files based on some thread identifier you defined in MDC

An example configuration is :

&lt;Appenders&gt;
   &lt;Routing name=&quot;Routing&quot;&gt;
			&lt;Routes pattern=&quot;$${ctx:threadId}&quot;&gt;
				&lt;Route&gt;
					&lt;File fileName=&quot;/logs/flyway-${ctx:threadId}.log&quot;
							name=&quot;flyway-${ctx:threadId}&quot;
							append=&quot;false&quot;&gt;						
					&lt;/File&gt;
				&lt;/Route&gt;
			&lt;/Routes&gt;
		&lt;/Routing&gt;
&lt;/Appenders&gt;


&lt;Loggers&gt;
   &lt;Logger name=&quot;org.flywaydb&quot; level=&quot;DEBUG&quot; &gt;
			&lt;AppenderRef ref=&quot;Routing&quot;/&gt;
	&lt;/Logger&gt;
&lt;/Loggers&gt;

In codes before you execute flyway , you configure a thread identifier and put it in MDC , something likes :

String threadId = threadId +  UUID.randomUUID().toString();

ThreadContext.put(&quot;threadId&quot;, threadId);

//execute flyway

//read all content from log to a string to further process
Path logFilePath = Path.of(&quot;/logs/flyway-&quot; + threadId + &quot;.log&quot;);
String logs = Files.readString(logFilePath);

ThreadContext.clearAll();

huangapple
  • 本文由 发表于 2023年3月3日 20:32:05
  • 转载请务必保留本文链接:https://go.coder-hub.com/75627119.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定