0

我开发了一个spring应用程序,我想用apache log4j配置它,已经下载了它并将jar放在项目的类路径中。下面是我的 log4j.Properties 文件。

# Root logger option
log4j.rootLogger=INFO, file
# Direct log messages to a log file
log4j.appender.file=org.apache.log4j.RollingFileAppender
log4j.appender.file.File=C\:\\loging.log
log4j.appender.file.MaxFileSize=1MB
log4j.appender.file.MaxBackupIndex=1
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%d{ABSOLUTE} %5p %c{1}:%L - %m%n

下面是我的主要弹簧应用程序类。

import org.apache.log4j.Logger;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.FileSystemResource;

public class DrawingClass {

    public static void main(String args[])
    {
        //without dependency injection 
        /*Triangle t1 = new Triangle();
        t1.draw();*/


        //with dependency injection     
        BeanFactory factory = new XmlBeanFactory(new FileSystemResource("Spring.xml"));
        Triangle t1 =(Triangle) factory.getBean("triangle");
        t1.draw();
    }
}

请告知我是否要将 log.info 放在上面的主类中我需要在我的主类中做哪些修改,还请告知我需要做哪些修改才能在我的主类中调用 log4j?

想出这个解决方案,它可以工作..编辑的 log4j.properties 文件是

### direct messages to file or.log ###
log4j.appender.file=org.apache.log4j.FileAppender
log4j.appender.file.File=C:/logs/s.log
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%d{ABSOLUTE} %5p %c{1} - %m%n
log4j.appender.file.append=true

### set log levels - for more verbose logging change 'info' to 'debug' ##
log4j.rootCategory=ALL, file
log4j.logger.Demo=\=debug
log4j.logger.org.eclipse=debug

从主类调用的方法是

import org.apache.log4j.Logger;
import org.apache.log4j.PropertyConfigurator;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.FileSystemResource;

public class DrawingClass {
     /* Get actual class name to be printed on */
    static final Logger log = Logger.getLogger(DrawingClass.class);
    public static void main(String args[])
    {PropertyConfigurator.configure("log4j.properties");
        //without dependency injection 
        /*Triangle t1 = new Triangle();
        t1.draw();*/

         log.info("Before execution");
        //with dependency injection     
        BeanFactory factory = new XmlBeanFactory(new FileSystemResource("Spring.xml"));
        Triangle t1 =(Triangle) factory.getBean("triangle");
        log.info("Hello this is an info message");
        t1.draw();
         log.info("after object execution");
    }
}

如果还有其他更好的方法,请指教。

4

3 回答 3

1

为了在我的项目中使用登录,我做了这样的事情:

1)定义的特殊注释应该标记应该注入记录器的字段:

@Retention(RUNTIME)  
@Target(FIELD)  
@Documented  
public @interface InjectLogger {  
}  

2)然后为注入记录器创建特殊的 BeanPostProcessor 到带注释的字段中:

@Component(value="loggerInjector")
public class LoggerInjector implements BeanPostProcessor {

    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName)
            throws BeansException {

        return bean;
    }

    @Override
    public Object postProcessBeforeInitialization(final Object bean, String beanName)
            throws BeansException {
        ReflectionUtils.doWithFields(bean.getClass(), new FieldCallback() {  
            public void doWith(Field field) throws IllegalArgumentException,  
            IllegalAccessException {  
                // make the field accessible if defined private  
                ReflectionUtils.makeAccessible(field);  
                if (field.getAnnotation(InjectLogger.class) != null) {  
                    Logger log = LoggerFactory.getLogger(bean.getClass()); 
                    field.set(bean, log);  
                }  
            }  
        });  
        return bean;  
    }  

}

3) 在此之后,在必要的 bean 标记属性中,应通过 @InjectLogger 注释注入记录器并在代码中使用此记录器。

    @InjectLogger
    private Logger logger;

public void doSomething(...) {
     try{
     ...
     } catch (Exception e) {
        logger.error("bla bla bla", e);
     }
}

在我的项目中,我使用 slf4j 和 log4j 作为具体实现。但是对于 log4j,它会是相似的。

您还需要知道默认情况下所有 Spring 库都使用 common-logging。如果您希望 Spring 库将其日志写入您的文件,您应该使用特殊的附加库。我记得,你可以从 appache 网站获得它们。对于 slf4j,这样的库被命名为 jcl-over-slf4j-1.6.4.jar。

编辑2:

同样在春季,好的做法是使用 AOP 进行日志记录。下面是一个简化的 Aspect 示例:

@Component
@Aspect
@Order(value=2)
public class LoggingAspect {

    @Around("execution(* com.blablabla.server..*.*(..))")
    public Object logMethod(ProceedingJoinPoint joinPoint) throws Throwable{
        final Logger logger = LoggerFactory.getLogger(joinPoint.getTarget().getClass().getName());
        Object retVal = null;

        try {
            StringBuffer startMessageStringBuffer = new StringBuffer();

            startMessageStringBuffer.append("Start method ");
            startMessageStringBuffer.append(joinPoint.getSignature().getName());
            startMessageStringBuffer.append("(");

            Object[] args = joinPoint.getArgs();
            for (int i = 0; i < args.length; i++) {
                startMessageStringBuffer.append(args[i]).append(",");
            }
            if (args.length > 0) {
                startMessageStringBuffer.deleteCharAt(startMessageStringBuffer.length() - 1);
            }

            startMessageStringBuffer.append(")");

            logger.trace(startMessageStringBuffer.toString());

            StopWatch stopWatch = new StopWatch();
            stopWatch.start();

            retVal = joinPoint.proceed();

            stopWatch.stop();

            StringBuffer endMessageStringBuffer = new StringBuffer();
            endMessageStringBuffer.append("Finish method ");
            endMessageStringBuffer.append(joinPoint.getSignature().getName());
            endMessageStringBuffer.append("(..); execution time: ");
            endMessageStringBuffer.append(stopWatch.getTotalTimeMillis());
            endMessageStringBuffer.append(" ms;");

            logger.trace(endMessageStringBuffer.toString());
        } catch (Throwable ex) {
            StringBuffer errorMessageStringBuffer = new StringBuffer();

             // Create error message 
             logger.error(errorMessageStringBuffer.toString(), e)

            throw ex;
        }

        return retVal;
    }
}
于 2012-07-02T07:22:55.500 回答
1

您可以尝试将此行添加到您的课程中吗?

public class DrawingClass {

   static final Logger log = Logger.getLogger(DrawingClass.class);

public static void main(String args[])
{
    //without dependency injection 
    /*Triangle t1 = new Triangle();
    t1.draw();*/

    log.info("Before execution");
    //with dependency injection     
    BeanFactory factory = new XmlBeanFactory(new FileSystemResource("Spring.xml"));
    Triangle t1 =(Triangle) factory.getBean("triangle");
    t1.draw();
}
 }

现在让我知道是否有任何内容添加到日志中。

此链接可能对您有所帮助 - http://www.dzone.com/tutorials/java/log4j/sample-log4j-properties-file-configuration-1.html

于 2012-07-02T07:26:28.550 回答
0

# LOG4J configuration
log4j.rootLogger= DEBUG, INFO, Appender1, Appender2
 
log4j.appender.Appender1=org.apache.log4j.ConsoleAppender
log4j.appender.Appender1.layout=org.apache.log4j.PatternLayout
log4j.appender.Appender1.layout.ConversionPattern=%-7p %d [%t] %c %x - %m%n
 
log4j.appender.Appender2=org.apache.log4j.FileAppender
log4j.appender.Appender2.File=D:/Project Log/Demo/demo.log
log4j.appender.Appender2.layout=org.apache.log4j.PatternLayout
log4j.appender.Appender2.layout.ConversionPattern=%-7p %d [%t] %c %x - %m%n

将此代码写入 src 文件夹的 Resources 文件夹中的 log4j.properties 中。

<dependency>
			<groupId>log4j</groupId>
			<artifactId>log4j</artifactId>
			<version>1.2.17</version>
</dependency>
将上述代码写入 porm.xml 文件或下载此依赖项的 jar。

<context:property-placeholder location="classpath:log4j.properties" />

在 spring-config.xml 之间和中编写上面的代码

package com.apmc.controller;

import org.apache.log4j.Logger;
import java.text.DateFormat;
import java.util.Date;
import com.apmc.Generic.RandomGenerator;//This my own made class So You need to create //RandomGenerator for use it


@Controller
public class StateController {
	
	private static Logger logger = Logger.getLogger(StateController.class);
	DateFormat df = new SimpleDateFormat("ddMMyyHHmmss");
	Date dateobj = new Date();
    int randNum = RandomGenerator.randInt(1000, 9999);
    String successMsg = "", errorMsg = "";

    @Autowired
	StateService stateService;
	
	List<State> newList = new ArrayList();

    @RequestMapping(value = "/Admin/admin/NewState_form")
	public ModelAndView stateForm(@ModelAttribute State state) {
    	
    try {
			logger.info("\n stateForm Started \n errorcode : "+errorcode);
			newList = stateService.loadAll();
			logger.info("\n stateForm Completed");
			errorMsg = "";
	}  catch (Exception e) {
			errorcode = ""+df.format(dateobj)+randNum;
			errorMsg = " New State Form Error \n Please contact Admin and errorcode:"                           +errorcode;
			successMsg = "";
			logger.error("error code for stateForm in StateController"                                            +df.format(dateobj)+" errorcode: "+errorcode);
	}
		
    return new ModelAndView("state").addObject("editState",                                                                             new State())
                                    .addObject("errorMsg", errorMsg)                                                         .addObject("showStateList",newList)
                                    .addObject("successMsg", successMsg);
    }
}

上面关于如何在 Controller 或任何 Java 类中使用日志的示例在这里我为错误跟踪创建错误代码显示使用 RandomGenerator.java 与错误进行通信,如下所示

package com.apmc.Generic;

import java.util.Random;

public class RandomGenerator {
	
	/**
	 * Returns a pseudo-random number between min and max, inclusive.
	 * The difference between min and max can be at most
	 * <code>Integer.MAX_VALUE - 1</code>.
	 *
	 * @param min Minimum value
	 * @param max Maximum value.  Must be greater than min.
	 * @return Integer between min and max, inclusive.
	 * @see java.util.Random#nextInt(int)
	 */
	public static int randInt(int min, int max) {

	    // NOTE: Usually this should be a field rather than a method
	    // variable so that it is not re-seeded every call.
	    Random rand = new Random();

	    // nextInt is normally exclusive of the top value,
	    // so add 1 to make it inclusive
	    int randomNum = rand.nextInt((max - min) + 1) + min;

	    return randomNum;
	}
}

于 2015-08-24T03:53:31.970 回答