001/* 002 * Logback: the reliable, generic, fast and flexible logging framework. 003 * Copyright (C) 1999-2026, QOS.ch. All rights reserved. 004 * 005 * This program and the accompanying materials are dual-licensed under 006 * either the terms of the Eclipse Public License v2.0 as published by 007 * the Eclipse Foundation 008 * 009 * or (per the licensee's choosing) 010 * 011 * under the terms of the GNU Lesser General Public License version 2.1 012 * as published by the Free Software Foundation. 013 */ 014package ch.qos.logback.core.rolling.helper; 015 016import java.io.File; 017import java.time.Instant; 018import java.util.Arrays; 019import java.util.Comparator; 020import java.util.Date; 021import java.util.regex.Matcher; 022import java.util.regex.Pattern; 023 024public class SizeAndTimeBasedArchiveRemover extends TimeBasedArchiveRemover { 025 026 protected static final int NO_INDEX = -1; 027 028 public SizeAndTimeBasedArchiveRemover(FileNamePattern fileNamePattern, RollingCalendar rc) { 029 super(fileNamePattern, rc); 030 } 031 032 /** 033 * @since 1.7.0 034 */ 035 public SizeAndTimeBasedArchiveRemover(FileNamePattern fileNamePattern, 036 FileNamePattern fileNamePatternWithoutCompSuffix, RollingCalendar rc) { 037 super(fileNamePattern, fileNamePatternWithoutCompSuffix, rc); 038 } 039 040 @Override 041 protected File[] getFilesInPeriod(Instant instantOfPeriodToClean) { 042 File archive0 = new File(fileNamePattern.convertMultipleArguments(instantOfPeriodToClean, 0)); 043 File parentDir = getParentDir(archive0); 044 String stemRegex = createStemRegex(instantOfPeriodToClean); 045 File[] matchingFileArray = FileFilterUtil.filesInFolderMatchingStemRegex(parentDir, stemRegex); 046 return matchingFileArray; 047 } 048 049 @Override 050 protected File[] getUncompressedFilesInPeriod(Instant instantOfPeriodToClean) { 051 if (fileNamePatternWithoutCompSuffix == null) { 052 return new File[0]; 053 } 054 File archive0 = new File(fileNamePatternWithoutCompSuffix.convertMultipleArguments(instantOfPeriodToClean, 0)); 055 File parentDir = getParentDir(archive0); 056 // matching is on the whole file name, so compressed files do not match 057 String stemRegex = FileFilterUtil.afterLastSlash(fileNamePatternWithoutCompSuffix.toRegexForFixedDate(instantOfPeriodToClean)); 058 return FileFilterUtil.filesInFolderMatchingStemRegex(parentDir, stemRegex); 059 } 060 061 @Override 062 protected void descendingSort(File[] matchingFileArray, Instant instant) { 063 064 String regexForIndexExtreaction = createStemRegex(instant); 065 final Pattern pattern = Pattern.compile(regexForIndexExtreaction); 066 067 Arrays.sort(matchingFileArray, new Comparator<File>() { 068 @Override 069 public int compare(final File f1, final File f2) { 070 071 int index1 = extractIndex(pattern, f1); 072 int index2 = extractIndex(pattern, f2); 073 074 if (index1 == index2) 075 return 0; 076 // descending sort, i.e. newest files first 077 if (index2 < index1) 078 return -1; 079 else 080 return 1; 081 } 082 083 private int extractIndex(Pattern pattern, File f1) { 084 Matcher matcher = pattern.matcher(f1.getName()); 085 if (matcher.find()) { 086 String indexAsStr = matcher.group(1); 087 088 if (indexAsStr == null || indexAsStr.isEmpty()) 089 return NO_INDEX; // unreachable code? 090 else 091 return Integer.parseInt(indexAsStr); 092 } else 093 return NO_INDEX; 094 } 095 }); 096 } 097 098 private String createStemRegex(final Instant instantOfPeriodToClean) { 099 String regex = fileNamePattern.toRegexForFixedDate(instantOfPeriodToClean); 100 return FileFilterUtil.afterLastSlash(regex); 101 } 102 103}