当前位置: 首页 > wzjs >正文

宁海企业网站建设网站推广与优化平台

宁海企业网站建设,网站推广与优化平台,定制网站建设多少钱,自己做的网站如何制作后台目录 一、环境说明 二、进行配置 1、pom.xml 2、log4j2.xml 3、CustomDataSourceProperties 4、ConfigReader 5、ConnectionFactory 连接工厂类,用于管理数据库连接 三、进行简单测试配置 1、LogUtils 2、LoginUserInfoHelper 3、LoginLogUtils 4、…

目录

一、环境说明     

二、进行配置

1、pom.xml

2、log4j2.xml

3、CustomDataSourceProperties

4、ConfigReader

5、ConnectionFactory 连接工厂类,用于管理数据库连接

三、进行简单测试配置

1、LogUtils

2、LoginUserInfoHelper

3、LoginLogUtils

4、写日志


一、环境说明     

        Spring Boot2+MyBatis-Plus+Log4j2

二、进行配置

1、pom.xml

        由于Spring Boot内置的日志框架是logback,会导致和log4j2冲突,所以要先排除项目中logback的依赖。同时引入log4j2。

        <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId><exclusions> <!-- 去掉springboot默认配置 --><exclusion><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-logging</artifactId></exclusion></exclusions></dependency><dependency> <!-- 引入log4j2依赖 --><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-log4j2</artifactId></dependency>

2、log4j2.xml

<?xml version="1.0" encoding="UTF-8"?>
<!--Configuration 标签用于配置 Log4j2,其中 status 属性设置为 "WARN",表示仅记录警告级别的日志用于运行时状态。monitorInterval 属性设置为 "30",表示每隔 30 秒自动检查配置文件更改。
-->
<Configuration status="WARN" monitorInterval="30"><Properties><!--定义名为 "baseDir" 的属性,用于指定日志文件的基本目录。其他地方可以使用 "${baseDir}" 引用这个值。--><Property name="baseDir">./logs</Property><!--定义名为 "logPattern" 的属性,用于指定日志的格式,以便在后续配置中引用。--><Property name="logPattern">%d{yyyy-MM-dd HH:mm:ss} %highlight{%6p} %style{%5pid}{bright,magenta} --- [%15.15t]%style{%-40.40logger{39}}{bright,cyan} : %m%n</Property><!-- 文件输出的格式 --><Property name="fileLayout">%d{yyyy-MM-dd HH:mm:ss} %p --- [%t] %logger : %m%n"</Property><!-- <Property name="logPattern">%highlight{%d{HH:mm:ss:SSS} [%-5p] - %l - %m%n}{FATAL=red, ERROR=red, WARN=yellow, INFO=default, DEBUG=default}</Property> --><!--定义名为 "fileSize" 的属性,用于指定日志文件的最大大小。其他地方可以使用 "${fileSize}" 引用这个值。--><Property name="fileSize">10MB</Property></Properties><!-- OFF	0 --><!-- FATAL	100 --><!-- ERROR	200 --><!-- WARN	300 --><!-- INFO	400 --><!-- DEBUG	500 --><!-- TRACE	600 --><!-- ALL	Integer.MAX_VALUE --><CustomLevels><CustomLevel name="CUSTOM_LOG" intLevel="90"/><CustomLevel name="EXCEPTION_LOG" intLevel="91"/><CustomLevel name="OPERATION_LOG" intLevel="92"/><CustomLevel name="LOGIN_LOG" intLevel="93"/></CustomLevels><Appenders><!-- Console Appender 用于将日志输出到控制台。--><Console name="Console" target="SYSTEM_OUT"><!-- 只输出 DEBUG 级别及以上的日志 --><ThresholdFilter level="DEBUG" onMatch="ACCEPT" onMismatch="DENY"/><!-- 使用定义的日志格式 --><PatternLayout pattern="${logPattern}"/></Console><!-- DEBUG 级别的日志文件输出 --><RollingFile name="DebugAppender" fileName="${baseDir}/app_debug.log"filePattern="${baseDir}/debug_%d{yyyy-MM-dd}_%i.log"><!-- 仅接受 DEBUG 级别的日志 --><Filters><ThresholdFilter level="DEBUG"/><ThresholdFilter level="INFO" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><!-- 使用定义的日志格式 --><PatternLayout pattern="${fileLayout}"/><Policies><!-- 每隔 1 天滚动一次日志,"modulate" 表示即使没有日志产生,也会在下一天创建新文件 --><TimeBasedTriggeringPolicy interval="1" modulate="true"/><!-- 当日志文件大小达到指定大小时触发滚动 --><SizeBasedTriggeringPolicy size="${fileSize}"/></Policies></RollingFile><!-- INFO 级别的日志文件输出 --><RollingFile name="InfoAppender" fileName="${baseDir}/app_info.log"filePattern="${baseDir}/info_%d{yyyy-MM-dd}_%i.log"><Filters><!-- 仅接受 INFO 级别的日志 --><!-- onMatch="ACCEPT" onMismatch="DENY" --><ThresholdFilter level="INFO"/><ThresholdFilter level="WARN" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><!-- 使用定义的日志格式 --><PatternLayout pattern="${fileLayout}"/><Policies><!-- 每隔 1 天滚动一次日志,"modulate" 表示即使没有日志产生,也会在下一天创建新文件 --><TimeBasedTriggeringPolicy interval="1" modulate="true"/><!-- 当日志文件大小达到指定大小时触发滚动 --><SizeBasedTriggeringPolicy size="${fileSize}"/></Policies></RollingFile><!--处理 WARN 级别的日志--><RollingFile name="WarnAppender" fileName="${baseDir}/app_warn.log"filePattern="${baseDir}/info_%d{yyyy-MM-dd}_%i.log"><Filters><ThresholdFilter level="WARN"/><ThresholdFilter level="ERROR" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><!-- 使用定义的日志格式 --><PatternLayout pattern="${fileLayout}"/><Policies><!-- 每隔 1 天滚动一次日志,"modulate" 表示即使没有日志产生,也会在下一天创建新文件 --><TimeBasedTriggeringPolicy interval="1" modulate="true"/><!-- 当日志文件大小达到指定大小时触发滚动 --><SizeBasedTriggeringPolicy size="${fileSize}"/></Policies></RollingFile><!-- ERROR 级别的日志文件输出 --><RollingFile name="ErrorAppender" fileName="${baseDir}/app_error.log"filePattern="${baseDir}/error_%d{yyyy-MM-dd}_%i.log"><!-- 仅接受 ERROR 级别的日志 --><Filters><ThresholdFilter level="ERROR"/><ThresholdFilter level="FATAL" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><!-- 使用定义的日志格式 --><PatternLayout pattern="${fileLayout}"/><Policies><!-- 每隔 1 天滚动一次日志,"modulate" 表示即使没有日志产生,也会在下一天创建新文件 --><TimeBasedTriggeringPolicy interval="1" modulate="true"/><!-- 当日志文件大小达到指定大小时触发滚动 --><SizeBasedTriggeringPolicy size="${fileSize}"/></Policies></RollingFile><!-- 配置 HikariSqlFile Appender,将 SQL 日志输出到文件的日志记录追加器 --><!-- <RollingFile name="HikariSqlAppender" fileName="${baseDir}/app_sql.log" --><!--              filePattern="${baseDir}/app_sql_%d{yyyy-MM-dd}_%i.log"> --><!--     &lt;!&ndash; 使用定义的日志格式 &ndash;&gt; --><!--     <PatternLayout pattern="${fileLayout}"/> --><!--     <Policies> --><!--         &lt;!&ndash; 每隔 1 天滚动一次日志,"modulate" 表示即使没有日志产生,也会在下一天创建新文件 &ndash;&gt; --><!--         <TimeBasedTriggeringPolicy interval="1" modulate="true"/> --><!--         &lt;!&ndash; 当日志文件大小达到指定大小时触发滚动 &ndash;&gt; --><!--         <SizeBasedTriggeringPolicy size="${fileSize}"/> --><!--     </Policies> --><!-- </RollingFile> --><!-- 配置JDBC Appender --><!-- 登录日志表 --><JDBC name="LoginDatabase" tableName="sys_log_login"><ConnectionFactory class="com.cj.blog.common.logs.ConnectionFactory" method="getDatabaseConnection"/><Filters><ThresholdFilter level="LOGIN_LOG"/><ThresholdFilter level="OPERATION_LOG" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><Column name="user_id" pattern="%X{user_id}"/><Column name="user_name" pattern="%X{user_name}"/><Column name="client_ip" pattern="%X{client_ip}"/><Column name="device_info" pattern="%X{device_info}"/><Column name="remarks" pattern="%X{remarks}"/><Column name="login_time" pattern="%d{yyyy-MM-dd HH:mm:ss}"/></JDBC><!-- 操作日志表 --><JDBC name="OperationDatabase" tableName="sys_log_operation"><ConnectionFactory class="com.cj.blog.common.logs.ConnectionFactory" method="getDatabaseConnection"/><Filters><ThresholdFilter level="OPERATION_LOG"/><ThresholdFilter level="EXCEPTION_LOG" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><Column name="user_id" pattern="%X{user_id}"/><Column name="user_name" pattern="%X{user_name}"/><Column name="v_before" pattern="%X{v_before}"/><Column name="v_after" pattern="%X{v_after}"/><Column name="remarks" pattern="%X{remarks}"/><Column name="operation_time" pattern="%d{yyyy-MM-dd HH:mm:ss}"/></JDBC><!-- 异常日志表 --><JDBC name="ExceptionDatabase" tableName="sys_log_exception"><ConnectionFactory class="com.cj.blog.common.logs.ConnectionFactory" method="getDatabaseConnection"/><Filters><ThresholdFilter level="EXCEPTION_LOG"/><ThresholdFilter level="CUSTOM_LOG" onMatch="DENY" onMismatch="NEUTRAL"/></Filters><Column name="user_id" pattern="%X{user_id}"/><Column name="user_name" pattern="%X{user_name}"/><Column name="request_mode" pattern="%X{request_mode}"/><Column name="absolute_uri" pattern="%X{absolute_uri}"/><Column name="form_data" pattern="%X{form_data}"/><Column name="source" pattern="%X{source}"/><Column name="message" pattern="%X{message}"/><!-- <Column name="stack_trace" pattern="%X{stack_trace}"/> --><Column name="exception_time" pattern="%d{yyyy-MM-dd HH:mm:ss}"/></JDBC></Appenders><Loggers><Root level="DEBUG"><!-- 控制台 --><AppenderRef ref="Console" level="INFO"/><!-- 文件 --><AppenderRef ref="ErrorAppender" level="ERROR"/><AppenderRef ref="WarnAppender" level="WARN"/><AppenderRef ref="InfoAppender" level="INFO"/><AppenderRef ref="DebugAppender" level="DEBUG"/><!-- 数据库源 --><AppenderRef ref="LoginDatabase" level="LOGIN_LOG"/><AppenderRef ref="OperationDatabase" level="OPERATION_LOG"/><AppenderRef ref="ExceptionDatabase" level="EXCEPTION_LOG"/></Root><!-- <Logger name="com.cj.config.logs.ConnectionFactory" level="INFO"> --><!--     <AppenderRef ref="DatabaseAppender" level="INFO"/> --><!-- </Logger> --><!-- <Root level="TRACE"> --><!--     &lt;!&ndash; 引用控制台输出和文件输出的 appender &ndash;&gt; --><!--     <AppenderRef ref="Console"/> --><!--     <AppenderRef ref="DebugAppender"/> --><!--     <AppenderRef ref="InfoAppender"/> --><!--     <AppenderRef ref="WarnAppender"/> --><!--     <AppenderRef ref="ErrorAppender"/> --><!--     <AppenderRef ref="LoginDatabase"/> --><!--     <AppenderRef ref="OperationDatabase" /> --><!--     &lt;!&ndash; <AppenderRef ref="ExceptionDatabase" level="Exception"/> &ndash;&gt; --><!-- </Root> --><Logger name="org.apache.logging.log4j" level="DEBUG" additivity="false"><AppenderRef ref="Console"/></Logger><!--额外配置的logger--><!--log4j2 自带过滤日志--><!-- Apache Tomcat Web服务器配置加载的日志 --><Logger name="org.apache.catalina.startup.DigesterFactory" level="ERROR"><!-- 仅记录错误级别的日志,通常用于记录严重的配置错误 --></Logger><!-- 与 Apache Tomcat 相关的组件生命周期信息 --><Logger name="org.apache.catalina.util.LifecycleBase" level="ERROR"><!-- 仅记录错误级别的信息 --></Logger><!-- Apache Tomcat HTTP 协议处理器的日志记录 --><Logger name="org.apache.coyote.http11.Http11NioProtocol" level="WARN"><!-- 记录警告级别及更高级别的信息,通常用于记录一般警告信息 --></Logger><!-- Apache SSHD(SSH Server)库的日志记录 --><Logger name="org.apache.sshd.common.util.SecurityUtils" level="WARN"><!-- 记录警告级别及更高级别的信息,通常用于记录一般警告信息 --></Logger><!-- 与 Apache Tomcat 相关的 NIO 选择器池的日志记录 --><Logger name="org.apache.tomcat.util.net.NioSelectorPool" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><!-- 与 CRaSH(Common Reusable SHell)相关的库和 SSH 支持的日志记录 --><Logger name="org.crsh.plugin" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><Logger name="org.crsh.ssh" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><!-- Eclipse Jetty Web服务器的组件生命周期的日志记录 --><Logger name="org.eclipse.jetty.util.component.AbstractLifeCycle" level="ERROR"><!-- 仅记录错误级别的信息 --></Logger><!-- Hibernate Validator相关日志 --><Logger name="org.hibernate.validator.internal.util.Version" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><!-- 与 Spring Boot Actuator 相关的日志记录 --><Logger name="org.springframework.boot.actuate.autoconfigure.CrshAutoConfiguration" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><Logger name="org.springframework.boot.actuate.endpoint.jmx" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger><!-- Thymeleaf模板引擎的日志记录 --><Logger name="org.thymeleaf" level="WARN"><!-- 记录警告级别及更高级别的信息 --></Logger></Loggers></Configuration>

3、CustomDataSourceProperties

import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;@Data
@Component
@ConfigurationProperties(prefix = "spring.datasource")
@Scope("singleton")
public class CustomDataSourceProperties {public String url;public String username;public String password;public String driverClassName;
}

4、ConfigReader

import com.cj.blog.model.base.CustomDataSourceProperties;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.dataformat.yaml.YAMLFactory;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;import java.io.InputStream;
import java.util.Map;/*** 用于从YAML文件中读取配置属性的实用工具类。*/
public class ConfigReader {private static final Logger logger = LogManager.getLogger(ConfigReader.class);/*** 从YAML配置文件中获取数据源属性。** @return CustomDataSourceProperties对象,包含数据源属性,如果未找到属性则返回null。*/public static CustomDataSourceProperties getDataSourceProperties() {String defaultActive = "dev"; // 默认活动配置String defaultConfigFile = "/application.yml"; // 默认配置文件名// 从默认配置文件中获取Spring属性Map<String, Object> properties = getSpringProperties(defaultActive, defaultConfigFile);if (properties != null) {Map<String, Object> springProperties = (Map<String, Object>) properties.get("spring");if (springProperties != null) {Map<String, Object> datasourceProperties = (Map<String, Object>) springProperties.get("datasource");if (datasourceProperties != null) {CustomDataSourceProperties dataSourceProperties = new CustomDataSourceProperties();dataSourceProperties.setUrl((String) datasourceProperties.get("url"));dataSourceProperties.setUsername((String) datasourceProperties.get("username"));dataSourceProperties.setPassword((String) datasourceProperties.get("password"));dataSourceProperties.setDriverClassName((String) datasourceProperties.get("driver-class-name"));logger.info("获取数据源属性成功!");logger.info("数据源属性:" + dataSourceProperties);return dataSourceProperties;}}}return null;}/*** 从指定的配置文件中获取Spring属性。** @param active     要使用的活动配置。* @param configFile 配置文件的路径。* @return 包含Spring属性的Map,如果未找到属性则返回null。*/private static Map<String, Object> getSpringProperties(String active, String configFile) {// 读取配置文件Map<String, Object> data = readConfigFile(configFile);if (data != null) {Map<String, Object> springProperties = (Map<String, Object>) data.get("spring");if (springProperties != null) {Map<String, Object> applicationProperties = (Map<String, Object>) springProperties.get("profiles");if (applicationProperties != null) {active = (String) applicationProperties.get("active");System.out.println("spring.application.active: " + active);}}}logger.info("spring.application.active: " + active);// 读取活动配置的配置文件return readConfigFile("/application-" + active + ".yml");}/*** 读取指定的YAML配置文件并将其解析为Map。** @param fileName YAML文件的路径。* @return 包含解析后的YAML数据的Map,如果未找到文件或无法解析则返回null。*/private static Map<String, Object> readConfigFile(String fileName) {try {// 创建用于解析YAML文件的ObjectMapper对象ObjectMapper mapper = new ObjectMapper(new YAMLFactory());// 使用类加载器加载YAML文件InputStream inputStream = ConfigReader.class.getResourceAsStream(fileName);// 读取YAML文件并解析为Map对象return mapper.readValue(inputStream, new TypeReference<Map<String, Object>>() {});} catch (Exception e) {e.printStackTrace();return null;}}}

5、ConnectionFactory 连接工厂类,用于管理数据库连接

import com.cj.blog.common.utils.ConfigReader;
import com.cj.blog.model.base.CustomDataSourceProperties;
import org.apache.commons.dbcp.DriverManagerConnectionFactory;
import org.apache.commons.dbcp.PoolableConnection;
import org.apache.commons.dbcp.PoolableConnectionFactory;
import org.apache.commons.dbcp.PoolingDataSource;
import org.apache.commons.pool.impl.GenericObjectPool;
import org.springframework.stereotype.Component;import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Properties;/*** 连接工厂类,用于管理数据库连接。通过Apache Commons DBCP提供数据库连接池功能。*/
@Component
public class ConnectionFactory {// 数据源,用于获取数据库连接private final DataSource dataSource;/*** 构造函数,初始化数据库连接池配置,并创建数据源。** @param dataSourceProperties 数据源属性对象,包含数据库连接信息*/public ConnectionFactory(CustomDataSourceProperties dataSourceProperties) {// 初始化数据库连接池配置Properties properties = new Properties();properties.setProperty("user", dataSourceProperties.getUsername());properties.setProperty("password", dataSourceProperties.getPassword());// 创建基于DriverManager的连接工厂和连接池GenericObjectPool<PoolableConnection> pool = new GenericObjectPool<>();pool.setMaxActive(10); // 设置最大连接数pool.setMinIdle(2); // 设置最小空闲连接数DriverManagerConnectionFactory connectionFactory = new DriverManagerConnectionFactory(dataSourceProperties.getUrl(), properties);// 创建可池化的数据库连接工厂new PoolableConnectionFactory(connectionFactory, pool, null, "SELECT 1", 3, false, false, Connection.TRANSACTION_READ_COMMITTED);// 创建数据源this.dataSource = new PoolingDataSource(pool);}/*** 获取数据库连接。** @return 数据库连接* @throws SQLException 如果获取连接时发生错误*/public static Connection getDatabaseConnection() throws SQLException {return Singleton.INSTANCE.dataSource.getConnection();}/*** 单例类,确保只有一个连接工厂实例。*/private static class Singleton {static ConnectionFactory INSTANCE;static {// TODO 这里需要修改,在创建数据库连接工厂时,需要从配置文件中读取数据源属性// 从配置文件中读取数据源属性,并创建连接工厂实例CustomDataSourceProperties dataSourceProperties = ConfigReader.getDataSourceProperties();dataSourceProperties.setDriverClassName(dataSourceProperties.getDriverClassName());dataSourceProperties.setUrl(dataSourceProperties.getUrl());dataSourceProperties.setUsername(dataSourceProperties.getUsername());dataSourceProperties.setPassword(dataSourceProperties.getPassword());INSTANCE = new ConnectionFactory(dataSourceProperties);}}}

三、进行简单测试配置

1、LogUtils

import org.apache.logging.log4j.ThreadContext;/*** 日志工具类*/
public class LogUtils {/*** 清除登录日志上下文信息,以便在日志记录操作结束后不保留上下文。*/public static void clearLogContext() {ThreadContext.clearMap();}
}

2、LoginUserInfoHelper

/*** 用于存储和获取用户信息的线程局部存储辅助类。*/
public class LoginUserInfoHelper {// 使用 ThreadLocal 来存储用户ID和用户名private static final ThreadLocal<Long> userId = new ThreadLocal<>();private static final ThreadLocal<String> userName = new ThreadLocal<>();/*** 获取当前线程的用户ID。** @return 用户ID*/public static Long getUserId() {return userId.get();}/*** 设置当前线程的用户ID。** @param _userId 用户ID*/public static void setUserId(Long _userId) {userId.set(_userId);}/*** 从当前线程中移除用户ID。*/public static void removeUserId() {userId.remove();}/*** 获取当前线程的用户名。** @return 用户名*/public static String getUsername() {return userName.get();}/*** 设置当前线程的用户名。** @param _username 用户名*/public static void setUsername(String _username) {userName.set(_username);}/*** 从当前线程中移除用户名。*/public static void removeUsername() {userName.remove();}
}

3、LoginLogUtils

import com.cj.blog.common.utils.RequestUtils;
import com.cj.blog.model.auth.LoginUserInfoHelper;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.ThreadContext;import javax.servlet.http.HttpServletRequest;
import java.util.Objects;
import java.util.Optional;/*** 登录日志工具类。*/
public class LoginLogUtils {private static final Logger logger = LogManager.getLogger(LoginLogUtils.class);/*** 设置用户登录日志,根据HttpServletRequest设置日志上下文信息。** @param request 请求对象,用于获取远程地址和用户代理信息。* @param remarks 登录日志的备注信息。*/public static void setLogLogin(HttpServletRequest request, String remarks) {// 使用 LoginUserInfoHelper 中的用户信息设置登录日志setLogLogin(LoginUserInfoHelper.getUserId().toString(),LoginUserInfoHelper.getUsername(),request.getRemoteAddr(),RequestUtils.getUserAgent(request),remarks);}/*** 设置用户登录日志,根据指定的客户端IP、设备信息和备注信息。** @param clientIp   客户端IP地址。* @param deviceInfo 设备信息。* @param remarks    登录日志的备注信息。*/public static void setLogLogin(String clientIp, String deviceInfo, String remarks) {// 使用 LoginUserInfoHelper 中的用户信息设置登录日志setLogLogin(LoginUserInfoHelper.getUserId().toString(),LoginUserInfoHelper.getUsername(),clientIp,deviceInfo,remarks);}/*** 设置用户登录日志,包含用户ID、用户名、客户端IP、设备信息和备注信息。** @param userId     用户ID。* @param userName   用户名。* @param clientIp   客户端IP地址。* @param deviceInfo 设备信息。* @param remarks    登录日志的备注信息。*/public static void setLogLogin(String userId, String userName, String clientIp, String deviceInfo, String remarks) {logLogin(userId, userName, clientIp, deviceInfo, remarks);}/*** 设置用户登录日志,包含用户ID、用户名、客户端IP、设备信息和备注信息。** @param userId     用户ID。* @param userName   用户名。* @param clientIp   客户端IP地址。* @param deviceInfo 设备信息。* @param remarks    登录日志的备注信息。*/public static void logLogin(String userId, String userName, String clientIp, String deviceInfo, String remarks) {try {// 设置上下文信息,这些信息将与日志消息关联ThreadContext.put("user_id", Objects.toString(userId, "0"));ThreadContext.put("user_name", Objects.toString(userName, "0"));ThreadContext.put("client_ip", clientIp);ThreadContext.put("device_info", deviceInfo);ThreadContext.put("remarks", remarks);// 使用自定义的 Login 级别记录消息logger.log(Level.getLevel("LOGIN_LOG"), remarks);} finally {LogUtils.clearLogContext(); // 在try块之后清除上下文,确保上下文信息不泄漏}}/*** 设置用户登录日志,包含用户ID、用户名、客户端IP、设备信息和备注信息。** @param clientIp   客户端IP地址。* @param deviceInfo 设备信息。* @param remarks    登录日志的备注信息。* @param userParams 用户ID、用户名。*/public static void setLogLogin(String clientIp, String deviceInfo, String remarks, String... userParams) {String userId = Optional.ofNullable(userParams.length > 0 ? userParams[0] : null).orElse("0");String userName = Optional.ofNullable(userParams.length > 1 ? userParams[1] : null).orElse("0");try {// 设置上下文信息,这些信息将与日志消息关联ThreadContext.put("user_id", userId);ThreadContext.put("user_name", userName);ThreadContext.put("client_ip", clientIp);ThreadContext.put("device_info", deviceInfo);ThreadContext.put("remarks", remarks);// 使用自定义的 Login 级别记录消息logger.log(Level.getLevel("LOGIN_LOG"), remarks);} finally {LogUtils.clearLogContext(); // 在try块之后清除上下文,确保上下文信息不泄漏}}}

4、写日志

        LoginLogUtils.setLogLogin(customUser.getSysUser().getUserId().toString(),customUser.getUsername(),request.getRemoteAddr(),RequestUtils.getUserAgent(request),"登录成功");
http://www.dtcms.com/wzjs/428902.html

相关文章:

  • 温江做网站的公司营销活动
  • 中山网站排名行业门户网站推广
  • 网络视频网站建设商业推广
  • 做公司网站的尺寸一般是多大如何在互联网推广自己的产品
  • 做网站如何让用户注册站长工具seo综合查询
  • 工业设计 做自己的网站 知乎网站快速排名推荐
  • 项城市建设方案公示在哪个网站seo专员很难吗
  • 北京模板网站建设费用培训课程网站
  • wordpress 设置站点地址seo品牌推广方法
  • 济宁百姓网免费发布信息网黑帽seo寄生虫
  • wordpress评论不准设置网站网站友情链接是什么
  • 做网站和网页有什么区别网络推广有哪些方法
  • 传奇广告查询网站磁力搜索器
  • 外链都没有的网站如何做排名的sem竞价托管费用
  • 一个域名可以做几个网站app优化排名
  • 河北新出现的传染病win优化大师有用吗
  • wordpress网页中添加3个音乐播放厦门seo搜索排名
  • 网站建设提示DNA错误网络seo软件
  • 建设部领导干部官方网站长春最新发布信息
  • 网站被降权会发生什么哪有恶意点击软件买的
  • 哪里有免费网站空间优化百度百科
  • 东莞专业做网站2024年新闻摘抄
  • 乌鲁木齐市最新消息今天优化seo方法
  • 那个网站点击率高seo去哪里学
  • 如何做视频会员网站百度认证服务平台
  • 短视频脚本制作教程网站收录优化
  • 给个做的网站吗媒体资源
  • 已经做好的网站怎么维护业务推广平台
  • 中企动力做的网站怎么样软文网
  • 保定制作公司网站百度关键词规划师工具