svn commit: r2384 - in logback/trunk/logback-core/src: main/java/ch/qos/logback/core/rolling main/java/ch/qos/logback/core/rolling/helper test/java/ch/qos/logback/core/rolling test/java/ch/qos/logback/core/rolling/helper

Author: ceki Date: Thu Jul 30 21:53:35 2009 New Revision: 2384 Added: logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicyTest.java Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/DefaultTimeBasedFileNamingAndTriggeringPolicy.java logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicy.java logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeBasedTriggeringPolicy.java logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/TimeBasedRollingPolicy.java logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/helper/FileNamePattern.java logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeBasedRollingTest.java logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/helper/FileNamePatternTest.java Log: ongoing work Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/DefaultTimeBasedFileNamingAndTriggeringPolicy.java ============================================================================== --- logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/DefaultTimeBasedFileNamingAndTriggeringPolicy.java (original) +++ logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/DefaultTimeBasedFileNamingAndTriggeringPolicy.java Thu Jul 30 21:53:35 2009 @@ -19,9 +19,9 @@ long time = getCurrentTime(); if (time >= nextCheck) { - Date dateInElapsedPeriod = dateInCurrentPeriod; + Date dateOfElapsedPeriod = dateInCurrentPeriod; elapsedPeriodsFileName = tbrp.fileNamePatternWCS - .convert(dateInElapsedPeriod); + .convert(dateOfElapsedPeriod); updateDateInCurrentPeriod(time); computeNextCheck(); return true; Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicy.java ============================================================================== --- logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicy.java (original) +++ logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicy.java Thu Jul 30 21:53:35 2009 @@ -12,27 +12,67 @@ import java.io.File; import java.util.Date; -public class SizeAndTimeBasedFileNamingAndTriggeringPolicy<E> extends TimeBasedFileNamingAndTriggeringPolicyBase<E> { +import ch.qos.logback.core.util.FileSize; +public class SizeAndTimeBasedFileNamingAndTriggeringPolicy<E> extends + TimeBasedFileNamingAndTriggeringPolicyBase<E> { + + int currentPeriodsCounter = 0; + FileSize maxFileSize; + String maxFileSizeAsString; @Override public void start() { super.start(); started = true; - } + } + + // IMPORTANT: This field can be updated by multiple threads. It follows that + // its values may *not* be incremented sequentially. However, we don't care + // about the actual value of the field except that from time to time the + // expression (invocationCounter++ & 0xF) == 0xF) should be true. + private int invocationCounter; public boolean isTriggeringEvent(File activeFile, final E event) { long time = getCurrentTime(); - if (time >= nextCheck) { Date dateInElapsedPeriod = dateInCurrentPeriod; elapsedPeriodsFileName = tbrp.fileNamePatternWCS - .convert(dateInElapsedPeriod); + .convertMultipleArguments(dateInElapsedPeriod, currentPeriodsCounter); + currentPeriodsCounter = 0; updateDateInCurrentPeriod(time); computeNextCheck(); return true; - } else { + } + + // for performance reasons, check for changes every 16 invocations + if (((invocationCounter++) & 0xF) != 0xF) { return false; } + + if (activeFile.length() >= maxFileSize.getSize()) { + elapsedPeriodsFileName = tbrp.fileNamePatternWCS + .convertMultipleArguments(dateInCurrentPeriod, currentPeriodsCounter); + currentPeriodsCounter++; + return true; + } + + return false; } + + @Override + public String getCurrentPeriodsFileNameWithoutCompressionSuffix() { + return tbrp.fileNamePatternWCS.convertMultipleArguments( + dateInCurrentPeriod, currentPeriodsCounter); + } + + public String getMaxFileSize() { + return maxFileSizeAsString; + } + + public void setMaxFileSize(String maxFileSize) { + this.maxFileSizeAsString = maxFileSize; + this.maxFileSize = FileSize.valueOf(maxFileSize); + } + } Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeBasedTriggeringPolicy.java ============================================================================== --- logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeBasedTriggeringPolicy.java (original) +++ logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/SizeBasedTriggeringPolicy.java Thu Jul 30 21:53:35 2009 @@ -15,37 +15,46 @@ import ch.qos.logback.core.util.FileSize; /** - * SizeBasedTriggeringPolicy looks at size of the file being - * currently written to. If it grows bigger than the specified size, - * the FileAppender using the SizeBasedTriggeringPolicy rolls the file - * and creates a new one. + * SizeBasedTriggeringPolicy looks at size of the file being currently written + * to. If it grows bigger than the specified size, the FileAppender using the + * SizeBasedTriggeringPolicy rolls the file and creates a new one. * * For more information about this policy, please refer to the online manual at * http://logback.qos.ch/manual/appenders.html#SizeBasedTriggeringPolicy * * @author Ceki Gülcü - * + * */ public class SizeBasedTriggeringPolicy<E> extends TriggeringPolicyBase<E> { - + public static final String SEE_SIZE_FORMAT = "http://logback.qos.ch/codes.html#sbtp_size_format"; /** * The default maximum file size. */ public static final long DEFAULT_MAX_FILE_SIZE = 10 * 1024 * 1024; // 10 MB - - String maxFileSizeAsString = Long.toString(DEFAULT_MAX_FILE_SIZE); + + String maxFileSizeAsString = Long.toString(DEFAULT_MAX_FILE_SIZE); FileSize maxFileSize; public SizeBasedTriggeringPolicy() { } public SizeBasedTriggeringPolicy(final String maxFileSize) { - setMaxFileSize(maxFileSize); + setMaxFileSize(maxFileSize); } + // IMPORTANT: This field can be updated by multiple threads. It follows that + // its values may *not* be incremented sequentially. However, we don't care + // about the actual value of the field except that from time to time the + // expression (invocationCounter++ & 0xF) == 0xF) should be true. + private int invocationCounter; + public boolean isTriggeringEvent(final File activeFile, final E event) { - //System.out.println("Size"+file.length()); + // for performance reasons, check for changes every 16 invocations + if (((invocationCounter++) & 0xF) != 0xF) { + return false; + } + return (activeFile.length() >= maxFileSize.getSize()); } @@ -57,36 +66,34 @@ this.maxFileSizeAsString = maxFileSize; this.maxFileSize = FileSize.valueOf(maxFileSize); } - + long toFileSize(String value) { - if(value == null) + if (value == null) return DEFAULT_MAX_FILE_SIZE; String s = value.trim().toUpperCase(); long multiplier = 1; int index; - if((index = s.indexOf("KB")) != -1) { + if ((index = s.indexOf("KB")) != -1) { multiplier = 1024; s = s.substring(0, index); - } - else if((index = s.indexOf("MB")) != -1) { - multiplier = 1024*1024; + } else if ((index = s.indexOf("MB")) != -1) { + multiplier = 1024 * 1024; s = s.substring(0, index); - } - else if((index = s.indexOf("GB")) != -1) { - multiplier = 1024*1024*1024; + } else if ((index = s.indexOf("GB")) != -1) { + multiplier = 1024 * 1024 * 1024; s = s.substring(0, index); } - if(s != null) { + if (s != null) { try { return Long.valueOf(s).longValue() * multiplier; - } - catch (NumberFormatException e) { - addError("[" + s + "] is not in proper int format. Please refer to "+SEE_SIZE_FORMAT); + } catch (NumberFormatException e) { + addError("[" + s + "] is not in proper int format. Please refer to " + + SEE_SIZE_FORMAT); addError("[" + value + "] not in expected format.", e); } } return DEFAULT_MAX_FILE_SIZE; - } + } } Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/TimeBasedRollingPolicy.java ============================================================================== --- logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/TimeBasedRollingPolicy.java (original) +++ logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/TimeBasedRollingPolicy.java Thu Jul 30 21:53:35 2009 @@ -46,8 +46,7 @@ private int maxHistory = NO_DELETE_HISTORY; private TimeBasedCleaner tbCleaner; - TimeBasedFileNamingAndTriggeringPolicy<E> timeBasedTriggering = new DefaultTimeBasedFileNamingAndTriggeringPolicy<E>(); - + TimeBasedFileNamingAndTriggeringPolicy<E> timeBasedTriggering; public void start() { // set the LR for our utility object renameUtil.setContext(this.context); @@ -72,6 +71,9 @@ addInfo("Will use the pattern " + fileNamePatternWCS + " for the active file"); + if(timeBasedTriggering == null) { + timeBasedTriggering = new DefaultTimeBasedFileNamingAndTriggeringPolicy<E>(); + } timeBasedTriggering.setContext(context); timeBasedTriggering.setTimeBasedRollingPolicy(this); timeBasedTriggering.start(); @@ -82,6 +84,10 @@ } } + public void setTimeBasedTriggering(TimeBasedFileNamingAndTriggeringPolicy<E> timeBasedTriggering) { + this.timeBasedTriggering = timeBasedTriggering; + } + static String computeFileNameStr_WCS(String fileNamePatternStr, CompressionMode compressionMode) { int len = fileNamePatternStr.length(); Modified: logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/helper/FileNamePattern.java ============================================================================== --- logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/helper/FileNamePattern.java (original) +++ logback/trunk/logback-core/src/main/java/ch/qos/logback/core/rolling/helper/FileNamePattern.java Thu Jul 30 21:53:35 2009 @@ -10,9 +10,7 @@ package ch.qos.logback.core.rolling.helper; -import java.util.Date; import java.util.HashMap; -import java.util.List; import java.util.Map; import ch.qos.logback.core.Context; @@ -94,7 +92,7 @@ } - public String convertList(List<Object> objectList) { + public String convertMultipleArguments(Object... objectList) { StringBuilder buf = new StringBuilder(); Converter<Object> c = headTokenConverter; while (c != null) { Added: logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicyTest.java ============================================================================== --- (empty file) +++ logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeAndTimeBasedFileNamingAndTriggeringPolicyTest.java Thu Jul 30 21:53:35 2009 @@ -0,0 +1,169 @@ +package ch.qos.logback.core.rolling; + +import static org.junit.Assert.assertTrue; + +import java.sql.Date; +import java.text.SimpleDateFormat; +import java.util.ArrayList; +import java.util.Calendar; +import java.util.List; + +import org.junit.Before; +import org.junit.Test; + +import ch.qos.logback.core.Context; +import ch.qos.logback.core.ContextBase; +import ch.qos.logback.core.layout.EchoLayout; +import ch.qos.logback.core.testUtil.RandomUtil; +import ch.qos.logback.core.util.Compare; +import ch.qos.logback.core.util.CoreTestConstants; + +public class SizeAndTimeBasedFileNamingAndTriggeringPolicyTest { + static final String DATE_PATTERN = "yyyy-MM-dd_HH_mm_ss"; + + int diff = RandomUtil.getPositiveInt(); + String randomOutputDir = CoreTestConstants.OUTPUT_DIR_PREFIX + "/" + diff + + "/"; + + SizeAndTimeBasedFileNamingAndTriggeringPolicy<Object> satbfnatPolicy = new SizeAndTimeBasedFileNamingAndTriggeringPolicy<Object>(); + + SimpleDateFormat sdf = new SimpleDateFormat(DATE_PATTERN); + + EchoLayout<Object> layout = new EchoLayout<Object>(); + Context context = new ContextBase(); + + RollingFileAppender<Object> rfa1 = new RollingFileAppender<Object>(); + TimeBasedRollingPolicy<Object> tbrp1 = new TimeBasedRollingPolicy<Object>(); + Calendar cal = Calendar.getInstance(); + long currentTime; // initialized in setUp() + long nextRolloverThreshold; // initialized in setUp() + List<String> expectedFilenameList = new ArrayList<String>(); + + int fileSize = 0; + int fileIndexCounter = 0; + int sizeThreshold; + + @Before + public void setUp() { + context.setName("test"); + cal.set(Calendar.MILLISECOND, 333); + currentTime = cal.getTimeInMillis(); + recomputeRolloverThreshold(currentTime); + System.out.println("at setUp() currentTime=" + + sdf.format(new Date(currentTime))); + + } + + // assuming rollover every second + void recomputeRolloverThreshold(long ct) { + long delta = ct % 1000; + nextRolloverThreshold = (ct - delta) + 1000; + } + + void initRFA(RollingFileAppender<Object> rfa, String filename) { + rfa.setContext(context); + rfa.setLayout(layout); + if (filename != null) { + rfa.setFile(filename); + } + } + + void initTRBP(RollingFileAppender<Object> rfa, TimeBasedRollingPolicy<Object> tbrp, + String filenamePattern, int sizeThreshold, long givenTime, long lastCheck) { + + tbrp.setContext(context); + satbfnatPolicy.setMaxFileSize(""+sizeThreshold); + tbrp.setTimeBasedTriggering(satbfnatPolicy); + tbrp.setFileNamePattern(filenamePattern); + tbrp.setParent(rfa); + tbrp.timeBasedTriggering.setCurrentTime(givenTime); + if (lastCheck != 0) { + tbrp.timeBasedTriggering.setDateInCurrentPeriod(new Date(lastCheck)); + } + rfa.setRollingPolicy(tbrp); + tbrp.start(); + rfa.start(); + } + + @Test + public void noCompression_FileBSet_NoRestart_1() throws Exception { + String testId = "test1"; + System.out.println(randomOutputDir); + String file = randomOutputDir + "toto.log"; + initRFA(rfa1, file); + sizeThreshold = 300; + initTRBP(rfa1, tbrp1, randomOutputDir + testId + "-%d{" + DATE_PATTERN + + "}-%i.txt", sizeThreshold, currentTime, 0); + + addExpectedFileName(testId, getDateOfCurrentPeriodsStart(), fileIndexCounter, false); + + incCurrentTime(100); + tbrp1.timeBasedTriggering.setCurrentTime(currentTime); + + for (int i = 0; i < 100; i++) { + String msg = "Hello -----------------" + i; + rfa1.doAppend(msg); + addExpectedFileNamedIfItsTime(testId, msg, false); + incCurrentTime(20); + tbrp1.timeBasedTriggering.setCurrentTime(currentTime); + } + + + massageExpectedFilesToCorresponToCurrentTarget(file); + int i = 0; + for (String fn : expectedFilenameList) { + System.out.println(fn); + //assertTrue(Compare.compare(fn, CoreTestConstants.TEST_DIR_PREFIX + // + "witness/rolling/satb-test1." + i++)); + } + } + + void massageExpectedFilesToCorresponToCurrentTarget(String file) { + // we added one too many files by date + expectedFilenameList.remove(expectedFilenameList.size() - 1); + expectedFilenameList.add(file); + } + + boolean passThresholdTime(long nextRolloverThreshold) { + return currentTime >= nextRolloverThreshold; + } + + void addExpectedFileNamedIfItsTime(String testId, String msg, boolean gzExtension) { + fileSize += msg.getBytes().length; + + if (passThresholdTime(nextRolloverThreshold)) { + fileIndexCounter = 0; + fileSize = 0; + addExpectedFileName(testId, getDateOfCurrentPeriodsStart(), fileIndexCounter, + gzExtension); + recomputeRolloverThreshold(currentTime); + return; + } + + // windows can delay file size changes + if((fileIndexCounter <= 1) && fileSize > sizeThreshold) { + addExpectedFileName(testId, getDateOfCurrentPeriodsStart(), ++fileIndexCounter, + gzExtension); + fileSize = 0; + return; + } + + } + + void addExpectedFileName(String testId, Date date, int fileIndexCounter, boolean gzExtension) { + String fn = CoreTestConstants.OUTPUT_DIR_PREFIX + testId + "-" + sdf.format(date)+"-"+fileIndexCounter+".txt"; + if (gzExtension) { + fn += ".gz"; + } + expectedFilenameList.add(fn); + } + + Date getDateOfCurrentPeriodsStart() { + long delta = currentTime % 1000; + return new Date(currentTime - delta); + } + + void incCurrentTime(long increment) { + currentTime += increment; + } +} Modified: logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeBasedRollingTest.java ============================================================================== --- logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeBasedRollingTest.java (original) +++ logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/SizeBasedRollingTest.java Thu Jul 30 21:53:35 2009 @@ -68,7 +68,7 @@ * ActiveFileName is not set. */ @Test - public void test1() throws Exception { + public void activeFileNameNotSet() throws Exception { // We purposefully use the \n as the line separator. // This makes the regression test system independent. Context context = new ContextBase(); @@ -101,7 +101,7 @@ * Test basic rolling functionality. */ @Test - public void test2() throws Exception { + public void smoke() throws Exception { Context context = new ContextBase(); DummyLayout<Object> layout = new DummyLayout<Object>("0123456789"); Modified: logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/helper/FileNamePatternTest.java ============================================================================== --- logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/helper/FileNamePatternTest.java (original) +++ logback/trunk/logback-core/src/test/java/ch/qos/logback/core/rolling/helper/FileNamePatternTest.java Thu Jul 30 21:53:35 2009 @@ -11,9 +11,7 @@ import static org.junit.Assert.assertEquals; -import java.util.ArrayList; import java.util.Calendar; -import java.util.List; import org.junit.Test; @@ -102,18 +100,10 @@ @Test public void objectListConverter() { - List<Object> oList = new ArrayList<Object>(); - Calendar cal = Calendar.getInstance(); cal.set(2003, 4, 20, 17, 55); - - oList.add(cal.getTime()); - oList.add(79); - - FileNamePattern fnp = new FileNamePattern("foo-%d{yyyy.MM.dd}-%i.txt", context); - - assertEquals("foo-2003.05.20-79.txt", fnp.convertList(oList)); + assertEquals("foo-2003.05.20-79.txt", fnp.convertMultipleArguments(cal.getTime(), 79)); } }
participants (1)
-
noreply.ceki@qos.ch