1 package org.apache.maven.archiva.consumers.core.repository;
4 * Licensed to the Apache Software Foundation (ASF) under one
5 * or more contributor license agreements. See the NOTICE file
6 * distributed with this work for additional information
7 * regarding copyright ownership. The ASF licenses this file
8 * to you under the Apache License, Version 2.0 (the
9 * "License"); you may not use this file except in compliance
10 * with the License. You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing,
15 * software distributed under the License is distributed on an
16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17 * KIND, either express or implied. See the License for the
18 * specific language governing permissions and limitations
22 import org.apache.commons.lang.time.DateUtils;
23 import org.apache.maven.archiva.common.utils.VersionComparator;
24 import org.apache.maven.archiva.common.utils.VersionUtil;
25 import org.apache.maven.archiva.database.ArtifactDAO;
26 import org.apache.maven.archiva.indexer.RepositoryContentIndex;
27 import org.apache.maven.archiva.model.ArtifactReference;
28 import org.apache.maven.archiva.model.VersionedReference;
29 import org.apache.maven.archiva.repository.ContentNotFoundException;
30 import org.apache.maven.archiva.repository.ManagedRepositoryContent;
31 import org.apache.maven.archiva.repository.layout.LayoutException;
34 import java.text.ParseException;
35 import java.text.SimpleDateFormat;
36 import java.util.ArrayList;
37 import java.util.Calendar;
38 import java.util.Collections;
39 import java.util.Date;
40 import java.util.List;
43 import java.util.regex.Matcher;
46 * Purge from repository all snapshots older than the specified days in the repository configuration.
48 * @author <a href="mailto:oching@apache.org">Maria Odea Ching</a>
50 public class DaysOldRepositoryPurge
51 extends AbstractRepositoryPurge
53 private SimpleDateFormat timestampParser;
55 private int daysOlder;
57 private int retentionCount;
59 public DaysOldRepositoryPurge( ManagedRepositoryContent repository, ArtifactDAO artifactDao,
60 int daysOlder, int retentionCount, Map<String, RepositoryContentIndex> indices )
62 super( repository, artifactDao, indices );
63 this.daysOlder = daysOlder;
64 this.retentionCount = retentionCount;
65 timestampParser = new SimpleDateFormat( "yyyyMMdd.HHmmss" );
66 timestampParser.setTimeZone( DateUtils.UTC_TIME_ZONE );
69 public void process( String path )
70 throws RepositoryPurgeException
74 File artifactFile = new File( repository.getRepoRoot(), path );
76 if ( !artifactFile.exists() )
81 ArtifactReference artifact = repository.toArtifactReference( path );
83 Calendar olderThanThisDate = Calendar.getInstance( DateUtils.UTC_TIME_ZONE );
84 olderThanThisDate.add( Calendar.DATE, -daysOlder );
86 // respect retention count
87 VersionedReference reference = new VersionedReference();
88 reference.setGroupId( artifact.getGroupId() );
89 reference.setArtifactId( artifact.getArtifactId() );
90 reference.setVersion( artifact.getVersion() );
92 List<String> versions = new ArrayList<String>( repository.getVersions( reference ) );
94 Collections.sort( versions, VersionComparator.getInstance() );
97 // Is this a generic snapshot "1.0-SNAPSHOT" ?
98 if ( VersionUtil.isGenericSnapshot( artifact.getVersion() ) )
100 if ( artifactFile.lastModified() < olderThanThisDate.getTimeInMillis() )
102 if ( retentionCount > versions.size() )
104 // Done. nothing to do here. skip it.
108 purgeArtifact( versions, artifactFile );
111 // Is this a timestamp snapshot "1.0-20070822.123456-42" ?
112 else if ( VersionUtil.isUniqueSnapshot( artifact.getVersion() ) )
114 Calendar timestampCal = uniqueSnapshotToCalendar( artifact.getVersion() );
116 if ( timestampCal.getTimeInMillis() < olderThanThisDate.getTimeInMillis() )
118 if ( retentionCount > versions.size() )
120 // Done. nothing to do here. skip it.
124 purgeArtifact( versions, artifactFile );
126 else if ( artifactFile.lastModified() < olderThanThisDate.getTimeInMillis() )
129 if ( retentionCount > versions.size() )
131 // Done. nothing to do here. skip it.
135 purgeArtifact( versions, artifactFile );
139 catch ( LayoutException le )
141 throw new RepositoryPurgeException( le.getMessage() );
143 catch ( ContentNotFoundException e )
145 throw new RepositoryPurgeException( e.getMessage() );
149 private Calendar uniqueSnapshotToCalendar( String version )
151 // The latestVersion will contain the full version string "1.0-alpha-5-20070821.213044-8"
152 // This needs to be broken down into ${base}-${timestamp}-${build_number}
154 Matcher m = VersionUtil.UNIQUE_SNAPSHOT_PATTERN.matcher( version );
157 Matcher mtimestamp = VersionUtil.TIMESTAMP_PATTERN.matcher( m.group( 2 ) );
158 if ( mtimestamp.matches() )
160 String tsDate = mtimestamp.group( 1 );
161 String tsTime = mtimestamp.group( 2 );
166 versionDate = timestampParser.parse( tsDate + "." + tsTime );
167 Calendar cal = Calendar.getInstance( DateUtils.UTC_TIME_ZONE );
168 cal.setTime( versionDate );
172 catch ( ParseException e )
182 private void doPurgeAllRelated( File artifactFile ) throws LayoutException
184 ArtifactReference reference = repository.toArtifactReference( artifactFile.getAbsolutePath() );
188 Set<ArtifactReference> related = repository.getRelatedArtifacts( reference );
191 catch ( ContentNotFoundException e )
193 // Nothing to do here.
198 private void purgeArtifact( List<String> versions, File artifactFile )
199 throws LayoutException
201 int countToPurge = versions.size() - retentionCount;
203 while( versions.iterator().hasNext() )
205 if ( countToPurge-- <= 0 )
209 doPurgeAllRelated( artifactFile );