WSO2 Log4J RollingFileAppender 在 wso2esb-4.8.1 中不起作用

WSO2 Log4J RollingFileAppendeder does not work in wso2esb-4.8.1

我们正在使用 WSO2esb-4.8.1。
默认情况下,log4j 属性使用

    log4j.appender.CARBON_LOGFILE=org.wso2.carbon.logging.appenders.CarbonDailyRollingFileAppender

我希望这是基于大小的滚动文件。根据 https://docs.wso2.com/display/Carbon420/Managing+Logs 上的文档,以下应该可以解决问题。

##comment the following
###log4j.appender.CARBON_LOGFILE=org.wso2.carbon.logging.appenders.CarbonDailyRollingFileAppender
##Add the followng
log4j.appender.CARBON_LOGFILE=org.apache.log4j.RollingFileAppender
log4j.appender.CARBON_LOGFILE.MaxFileSize=10MB 
log4j.appender.CARBON_LOGFILE.MaxBackupIndex=20

但经过这些更改后,日志以 10MB 的速度旋转,但只保留一个文件。

这是 WSO2 ESB 4.8.1 中的已知问题吗?

这在 WSO2 ESB 4.9.0 中运行良好。

但是,我们没有升级到该版本的选项,因为我们需要的其他一些功能在那里被破坏了。 最后,我在 wso2 任务中模拟了日志轮换行为。请参阅 https://docs.wso2.com/display/ESB481/Writing+Tasks+Sample 以了解如何编写示例 WSo2 任务。

这是代码

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.channels.FileChannel;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Date;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.synapse.ManagedLifecycle;
import org.apache.synapse.core.SynapseEnvironment;
import org.apache.synapse.task.Task;

public class LogFileBackupTaskSample implements Task, ManagedLifecycle 
{
    private static final Log LOG = LogFactory.getLog(LogFileBackupTask.class);
    private SynapseEnvironment synapseEnvironment;

    // By default, the program is assumed to run from the WSO2 Home Folder
    public static final String DEFAULT_LOG_FILE_LOCATION ="repository/logs/";
    public static final String WSO2_LOG_FILE_NAME ="wso2carbon.log";
    // If a value is not provided for logFileSizeInMbStr, backup of the LOG file size would happen after it reaches 100 MB
    public static final int DEFAULT_LOG_FILE_SIZE_IN_MB =100;
    // If a value is not provided for noOfBackupFiles, 20 files would be backed up.
    public static final int DEFAULT_BACKUP_FILES_NUMBER =20;
    public static final int MB_TO_BYTES=1024 *1000; 
    private String logLocation;
    private int logFileSizeInMb;
    private String logFileSizeInMbStr;
    private String noOfBackupFiles;
    private int noOfBackupFilesInt;


    public void execute() 
    {
        FileChannel sourceChannel = null;
        FileChannel outChannel = null;
        if(logLocation==null  || logLocation.trim().equals(""))
        {
            if(LOG.isInfoEnabled())
            {
                LOG.info("No LOG location provided. Therefore using the default location of "+DEFAULT_LOG_FILE_LOCATION);
            }
            logLocation= DEFAULT_LOG_FILE_LOCATION;
        }
        if(!logLocation.endsWith("/") && !logLocation.endsWith("\"))
        {
            logLocation= logLocation+File.separator; 
        }
        if(logFileSizeInMb==0)
        {
            if(LOG.isInfoEnabled())
            {
                LOG.info("No LOG file size in MB. Therefore using the default size of "+DEFAULT_LOG_FILE_SIZE_IN_MB+" Mb");
            }
            logFileSizeInMb= DEFAULT_LOG_FILE_SIZE_IN_MB * MB_TO_BYTES;
        }
        String inputLogFileNameWithDirectory= logLocation+WSO2_LOG_FILE_NAME;
        File inputLogFileWithDirectory = new File(inputLogFileNameWithDirectory);
        long currentLogSize=0;
        boolean fileSwapped= false;

        try
        {

            currentLogSize = inputLogFileWithDirectory.length();            
            if(currentLogSize> logFileSizeInMb)
            {
                long currentDateLong = System.currentTimeMillis();
                Date  date = new Date(currentDateLong);
                String outFileName= WSO2_LOG_FILE_NAME+"."+date.toString().replace(' ', '_').replace(':', '_');
                sourceChannel = new FileInputStream(inputLogFileWithDirectory).getChannel();
                File outFile = new File (logLocation+outFileName);
                outFile.createNewFile();
                outChannel = new FileOutputStream(outFile).getChannel();
                outChannel.transferFrom(sourceChannel, 0, currentLogSize);
                fileSwapped= true;

            }
        }
        catch(IOException e)
        {
            LOG.error(e.toString(),e);
            throw new RuntimeException(e);
        }
        finally
        {
            if(sourceChannel!=null)
            {
                try
                {
                    sourceChannel.close();
                } 
                catch (IOException e) {
                    // Ignored 
                    LOG.error(e.toString(),e);
                }
            }
            if(outChannel!=null)
            {
                try
                {
                    outChannel.close();
                } 
                catch (IOException e) {
                    // Ignored 
                    LOG.error(e.toString(),e);
                }
            }


        }

        FileChannel sourceTruncateChannel = null; 
        try
        {
            if(fileSwapped)
            {
                sourceTruncateChannel = new FileOutputStream(inputLogFileWithDirectory).getChannel();
                sourceTruncateChannel.truncate(currentLogSize);
            }
        }
        catch(IOException e)
        {
            LOG.error(e.toString(),e);
            throw new RuntimeException(e);
        }
        finally
        {

            if(sourceTruncateChannel!=null)
            {
                try
                {
                    sourceTruncateChannel.close();
                } 
                catch (IOException e) {
                    // Ignored 
                    LOG.error(e.toString(),e);
                }
            }
        }
        if(fileSwapped)
        {
            deletingOldFiles();

        }
    }

    public void deletingOldFiles() 
    {

        if(noOfBackupFilesInt==0)
        {
            if(LOG.isInfoEnabled())
            {
                LOG.info("NoOfBackupFiles 0. Thus using the default number of "+DEFAULT_BACKUP_FILES_NUMBER);
            }
            noOfBackupFilesInt= DEFAULT_BACKUP_FILES_NUMBER;
        }
        File[] listOfFiles= new File(logLocation).listFiles();
        List <TimeStampWiseFile> listOfWso2Files = new ArrayList<TimeStampWiseFile>();
        for (int i = 0; i < listOfFiles.length; i++) 
        {
            if(listOfFiles[i].getName().startsWith(WSO2_LOG_FILE_NAME)  && !listOfFiles[i].getName().equals(WSO2_LOG_FILE_NAME))
            {
                listOfWso2Files.add(new TimeStampWiseFile(logLocation, listOfFiles[i].getName()));
            }               
        }
        // No files to delete in this case. 
        if(listOfWso2Files.size()<=noOfBackupFilesInt)
        {
            return;
        }
        TimeStampWiseFile[]   listOfWSo2FilesArray = new TimeStampWiseFile[listOfWso2Files.size()];
        listOfWSo2FilesArray=  listOfWso2Files.toArray(listOfWSo2FilesArray);
        // We need in descending order so that the old files are arranged at the bottom of the stack.
        Arrays.sort(listOfWSo2FilesArray, Collections.reverseOrder());

        int index=0;
        for (int i = 0; i < listOfWSo2FilesArray.length; i++) 
        {
            TimeStampWiseFile timeStampWiseFile = listOfWSo2FilesArray[i];
            if(++index > noOfBackupFilesInt)
            {
                String fileName = timeStampWiseFile.getName();
                timeStampWiseFile.delete();
                if(LOG.isInfoEnabled())
                {
                    LOG.info("Removed File  "+fileName);
                }

            }
        }

    }

    public void destroy() 
    {
    }

    public void init(SynapseEnvironment synapseEnvironment) 
    {
        this.synapseEnvironment = synapseEnvironment;
    }




        public String getLogLocation() 
        {
            return logLocation;
        }

        public void setLogLocation(String logLocation)
        {
            this.logLocation = logLocation;
            if(logLocation== null || logLocation.trim().equals(""))
            {
                if(LOG.isInfoEnabled())
                {
                    LOG.info("No LOG location provided. Therefore using the default location of "+DEFAULT_LOG_FILE_LOCATION);
                }
                logLocation= DEFAULT_LOG_FILE_LOCATION;
            }
        }

        public String getLogFileSizeInMbStr() 
        {
            return logFileSizeInMbStr;
        }

        public void setLogFileSizeInMbStr(String logFileSizeInMbStr) 
        {
            this.logFileSizeInMbStr = logFileSizeInMbStr;
            if(logFileSizeInMbStr== null || logFileSizeInMbStr.trim().equals(""))
            {
                if(LOG.isInfoEnabled())
                {
                    LOG.info("No LOG file size in MB. Therefore using the default size of "+DEFAULT_LOG_FILE_SIZE_IN_MB+" Mb");
                }
                logFileSizeInMb= DEFAULT_LOG_FILE_SIZE_IN_MB * MB_TO_BYTES;
            }
            else
            {

                try
                {
                    logFileSizeInMb= Integer.parseInt(logFileSizeInMbStr) * MB_TO_BYTES;
                }
                catch(NumberFormatException e)
                {
                    LOG.error("logFileSizeInMb is not proper. If the size is 20MB, provide 20 as the 2nd argument. Due to the exception"
                            + "using the default size of "+DEFAULT_LOG_FILE_SIZE_IN_MB+" Mb");
                    logFileSizeInMb= DEFAULT_LOG_FILE_SIZE_IN_MB * MB_TO_BYTES;
                }

            }

        }

        public String getNoOfBackupFiles() 
        {
            return noOfBackupFiles;
        }

        public void setNoOfBackupFiles(String noOfBackupFiles) 
        {
            this.noOfBackupFiles = noOfBackupFiles;
            try
            {
                noOfBackupFilesInt= Integer.parseInt(noOfBackupFiles) ;
            }
            catch(NumberFormatException e)
            {
                LOG.error("NoOfBackupFiles is not proper. Proper a proper integer value. Due to the exception"
                            + "using the default number of "+DEFAULT_BACKUP_FILES_NUMBER);
                noOfBackupFilesInt= DEFAULT_BACKUP_FILES_NUMBER;
            }
        }
}

现在仅在主租户中将其添加为计划。有关详细信息,请参阅 https://docs.wso2.com/display/ESB480/Adding+and+Scheduling+Tasks

<?xml version="1.0" encoding="UTF-8"?>
<task xmlns="http://ws.apache.org/ns/synapse"
      name="LogFileBackupTask"
      class="LogFileBackupTask"
      group="synapse.simple.quartz">
   <trigger cron="0 0/1 * * * ?"/>
   <property xmlns:task="http://www.wso2.org/products/wso2commons/tasks"
             name="noOfBackupFiles"
             value="20"/>
   <property xmlns:task="http://www.wso2.org/products/wso2commons/tasks"
             name="logFileSizeInMbStr"
             value="20"/>
   <property xmlns:task="http://www.wso2.org/products/wso2commons/tasks"
             name="logLocation"
             value="repository/logs/"/>
</task>