[MRM-564] Audit log is not populated when artifacts are deployed.

Expanded Audit concepts into listener / event / log.
Using log4j for audit log (for consistency with other logging)
Moved AuditLog from webapp to repository-layer.




git-svn-id: https://svn.apache.org/repos/asf/maven/archiva/trunk@593246 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Joakim Erdfelt 2007-11-08 18:36:12 +00:00
parent 9f4dee3c71
commit 729ad246d2
10 changed files with 389 additions and 360 deletions

View File

@ -0,0 +1,112 @@
package org.apache.maven.archiva.repository.audit;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
/**
* AuditEvent
*
* @author <a href="mailto:joakime@apache.org">Joakim Erdfelt</a>
* @version $Id$
*/
public class AuditEvent
{
public static final String CREATE_DIR = "Created Directory";
public static final String CREATE_FILE = "Created File";
public static final String REMOVE_DIR = "Removed Directory";
public static final String REMOVE_FILE = "Removed File";
public static final String MODIFY_FILE = "Modify File";
private String repositoryId;
private String userId;
private String remoteIP;
private String resource;
private String action;
public AuditEvent()
{
/* do nothing */
}
public AuditEvent( String repoId, String user, String resource, String action )
{
this.repositoryId = repoId;
this.userId = user;
this.resource = resource;
this.action = action;
}
public String getRepositoryId()
{
return repositoryId;
}
public void setRepositoryId( String repositoryId )
{
this.repositoryId = repositoryId;
}
public String getUserId()
{
return userId;
}
public void setUserId( String userId )
{
this.userId = userId;
}
public String getResource()
{
return resource;
}
public void setResource( String resource )
{
this.resource = resource;
}
public String getAction()
{
return action;
}
public void setAction( String action )
{
this.action = action;
}
public String getRemoteIP()
{
return remoteIP;
}
public void setRemoteIP( String remoteIP )
{
this.remoteIP = remoteIP;
}
}

View File

@ -0,0 +1,36 @@
package org.apache.maven.archiva.repository.audit;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
/**
* AuditListener
*
* @author <a href="mailto:joakime@apache.org">Joakim Erdfelt</a>
* @version $Id$
*/
public interface AuditListener
{
/**
* Notification that an audit event occured.
*
* @param event the event details.
*/
public void auditEvent( AuditEvent event );
}

View File

@ -0,0 +1,56 @@
package org.apache.maven.archiva.repository.audit;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import org.apache.log4j.Logger;
/**
* AuditLog - Audit Log.
*
* @author <a href="mailto:joakime@apache.org">Joakim Erdfelt</a>
* @version $Id$
*
* @plexus.component role="org.apache.maven.archiva.repository.audit.AuditListener"
* role-hint="logging"
*/
public class AuditLog
implements AuditListener
{
public static final Logger logger = Logger.getLogger( "org.apache.archiva.AuditLog" );
private static final char DELIM = ' ';
/**
* Creates a log message in the following format ...
*
* "{repository_id} {user_id} {remote_ip} \"{resource}\" \"{action}\""
*/
public void auditEvent( AuditEvent event )
{
StringBuffer msg = new StringBuffer();
msg.append( event.getRepositoryId() ).append( DELIM );
msg.append( event.getUserId() ).append( DELIM );
msg.append( event.getRemoteIP() ).append( DELIM );
msg.append( '\"' ).append( event.getResource() ).append( '\"' ).append( DELIM );
msg.append( '\"' ).append( event.getAction() ).append( '\"' );
logger.info( msg.toString() );
}
}

View File

@ -0,0 +1,48 @@
package org.apache.maven.archiva.repository.audit;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
/**
* Auditable
*
* @author <a href="mailto:joakime@apache.org">Joakim Erdfelt</a>
* @version $Id$
*/
public interface Auditable
{
/**
* Add an AuditListener.
*
* @param the listener to add.
*/
public void addAuditListener( AuditListener auditListener );
/**
* Remove an AuditListener.
*
* @param the listener to remove.
*/
public void removeAuditListener( AuditListener auditListener );
/**
* Remove all registered {@link AuditListener} objects.
*/
public void clearAuditListeners();
}

View File

@ -420,7 +420,6 @@
</roleDefaults>
</configuration>
</plugin>
<!--
<plugin>
<artifactId>maven-antrun-plugin</artifactId>
<executions>
@ -439,7 +438,6 @@
</execution>
</executions>
</plugin>
-->
</plugins>
</build>
<profiles>

View File

@ -1,169 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<version>2</version>
<managedRepositories>
<managedRepository>
<id>internal</id>
<name>Archiva Managed Internal Repository</name>
<location>${appserver.base}/data/repositories/internal</location>
<layout>default</layout>
<releases>true</releases>
<snapshots>false</snapshots>
<scanned>true</scanned>
<refreshCronExpression>0 0 0 * * ?</refreshCronExpression>
<daysOlder>30</daysOlder>
</managedRepository>
<managedRepository>
<id>snapshots</id>
<name>Archiva Managed Snapshot Repository</name>
<location>${appserver.base}/data/repositories/snapshots</location>
<layout>default</layout>
<releases>false</releases>
<snapshots>true</snapshots>
<scanned>true</scanned>
<refreshCronExpression>0 0\,30 0 * * ?</refreshCronExpression>
<daysOlder>30</daysOlder>
</managedRepository>
</managedRepositories>
<remoteRepositories>
<remoteRepository>
<id>central</id>
<name>Central Repository</name>
<url>http://repo1.maven.org/maven2</url>
<layout>default</layout>
</remoteRepository>
<remoteRepository>
<id>maven2-repository.dev.java.net</id>
<name>Java.net Repository for Maven 2</name>
<url>http://download.java.net/maven/2/</url>
<layout>default</layout>
</remoteRepository>
</remoteRepositories>
<proxyConnectors>
<proxyConnector>
<sourceRepoId>internal</sourceRepoId>
<targetRepoId>central</targetRepoId>
<proxyId/>
<policies>
<snapshots>disabled</snapshots>
<releases>once</releases>
<checksum>fix</checksum>
<cache-failures>cached</cache-failures>
</policies>
<whiteListPatterns>
<whiteListPattern>**/*</whiteListPattern>
</whiteListPatterns>
</proxyConnector>
<proxyConnector>
<sourceRepoId>internal</sourceRepoId>
<targetRepoId>maven2-repository.dev.java.net</targetRepoId>
<proxyId/>
<policies>
<snapshots>disabled</snapshots>
<releases>once</releases>
<checksum>fix</checksum>
<cache-failures>cached</cache-failures>
</policies>
<whiteListPatterns>
<whiteListPattern>javax/**</whiteListPattern>
</whiteListPatterns>
</proxyConnector>
</proxyConnectors>
<repositoryScanning>
<fileTypes>
<fileType>
<id>artifacts</id>
<patterns>
<pattern>**/*.pom</pattern>
<pattern>**/*.jar</pattern>
<pattern>**/*.ear</pattern>
<pattern>**/*.war</pattern>
<pattern>**/*.car</pattern>
<pattern>**/*.sar</pattern>
<pattern>**/*.mar</pattern>
<pattern>**/*.rar</pattern>
<pattern>**/*.dtd</pattern>
<pattern>**/*.tld</pattern>
<pattern>**/*.tar.gz</pattern>
<pattern>**/*.tar.bz2</pattern>
<pattern>**/*.zip</pattern>
</patterns>
</fileType>
<fileType>
<id>indexable-content</id>
<patterns>
<pattern>**/*.txt</pattern>
<pattern>**/*.TXT</pattern>
<pattern>**/*.block</pattern>
<pattern>**/*.config</pattern>
<pattern>**/*.pom</pattern>
<pattern>**/*.xml</pattern>
<pattern>**/*.xsd</pattern>
<pattern>**/*.dtd</pattern>
<pattern>**/*.tld</pattern>
</patterns>
</fileType>
<fileType>
<id>auto-remove</id>
<patterns>
<pattern>**/*.bak</pattern>
<pattern>**/*~</pattern>
<pattern>**/*-</pattern>
</patterns>
</fileType>
<fileType>
<id>ignored</id>
<patterns>
<pattern>**/.htaccess</pattern>
<pattern>**/KEYS</pattern>
<pattern>**/*.rb</pattern>
<pattern>**/*.sh</pattern>
<pattern>**/.svn/**</pattern>
<pattern>**/.DAV/**</pattern>
</patterns>
</fileType>
</fileTypes>
<knownContentConsumers>
<knownContentConsumer>update-db-artifact</knownContentConsumer>
<knownContentConsumer>create-missing-checksums</knownContentConsumer>
<knownContentConsumer>update-db-repository-metadata</knownContentConsumer>
<knownContentConsumer>validate-checksum</knownContentConsumer>
<knownContentConsumer>validate-signature</knownContentConsumer>
<knownContentConsumer>index-content</knownContentConsumer>
<knownContentConsumer>auto-remove</knownContentConsumer>
<knownContentConsumer>auto-rename</knownContentConsumer>
<knownContentConsumer>metadata-updater</knownContentConsumer>
<!--knownContentConsumer>repository-purge</knownContentConsumer-->
</knownContentConsumers>
<invalidContentConsumers>
<invalidContentConsumer>update-db-bad-content</invalidContentConsumer>
</invalidContentConsumers>
</repositoryScanning>
<databaseScanning>
<cronExpression>0 0 0 * * ?</cronExpression>
<unprocessedConsumers>
<unprocessedConsumer>index-artifact</unprocessedConsumer>
<unprocessedConsumer>update-db-project</unprocessedConsumer>
<unprocessedConsumer>validate-repository-metadata</unprocessedConsumer>
<unprocessedConsumer>index-archive-toc</unprocessedConsumer>
<unprocessedConsumer>update-db-bytecode-stats</unprocessedConsumer>
<unprocessedConsumer>index-public-methods</unprocessedConsumer>
</unprocessedConsumers>
<cleanupConsumers>
<cleanupConsumer>not-present-remove-db-artifact</cleanupConsumer>
<cleanupConsumer>not-present-remove-db-project</cleanupConsumer>
<cleanupConsumer>not-present-remove-indexed</cleanupConsumer>
</cleanupConsumers>
</databaseScanning>
<webapp>
<ui>
<showFindArtifacts>true</showFindArtifacts>
<appletFindEnabled>true</appletFindEnabled>
</ui>
</webapp>
</configuration>

View File

@ -1,165 +0,0 @@
package org.apache.maven.archiva.web.repository;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import org.apache.commons.lang.StringUtils;
import org.codehaus.plexus.evaluator.EvaluatorException;
import org.codehaus.plexus.evaluator.ExpressionEvaluator;
import org.codehaus.plexus.evaluator.ExpressionSource;
import org.codehaus.plexus.personality.plexus.lifecycle.phase.Initializable;
import org.codehaus.plexus.personality.plexus.lifecycle.phase.InitializationException;
import org.codehaus.plexus.webdav.DavServerComponent;
import org.codehaus.plexus.webdav.DavServerListener;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.PrintWriter;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* AuditLog - Audit Log.
*
* @author <a href="mailto:joakime@apache.org">Joakim Erdfelt</a>
* @version $Id$
*
* @plexus.component role="org.apache.maven.archiva.web.repository.AuditLog"
*/
public class AuditLog
implements DavServerListener, Initializable
{
public static final String ROLE = AuditLog.class.getName();
/**
* @plexus.configuration default-value="${appserver.base}/logs/audit.log"
*/
private String logFilename;
/**
* @plexus.configuration default-value="yyyy-MM-dd HH:mm:ss"
*/
private String timestampFormat;
/**
* @plexus.requirement role-hint="default"
*/
private ExpressionEvaluator expressionEvaluator;
/**
* @plexus.requirement role-hint="sysprops"
*/
private ExpressionSource syspropExprSource;
private File logFile;
private PrintWriter writer;
private SimpleDateFormat timestamp;
private String getServerId( DavServerComponent server )
{
return "[" + server.getPrefix() + "]";
}
public void serverCollectionCreated( DavServerComponent server, String resource )
{
log( getServerId( server ) + " Created Directory \"" + resource + "\"" );
}
public void serverCollectionRemoved( DavServerComponent server, String resource )
{
log( getServerId( server ) + " Removed Directory \"" + resource + "\"" );
}
public void serverResourceCreated( DavServerComponent server, String resource )
{
log( getServerId( server ) + " Created File \"" + resource + "\"" );
}
public void serverResourceModified( DavServerComponent server, String resource )
{
log( getServerId( server ) + " Modified Existing File \"" + resource + "\"" );
}
public void serverResourceRemoved( DavServerComponent server, String resource )
{
log( getServerId( server ) + " Removed File \"" + resource + "\"" );
}
/**
* Log the message to the file.
*
* @param msg the message.
*/
public void log( String msg )
{
// Synchronize to prevent threading issues.
synchronized ( writer )
{
writer.println( timestamp.format( new Date() ) + " - " + msg );
// Manually flush buffer to ensure data is written to disk.
writer.flush();
}
}
public void initialize()
throws InitializationException
{
String actualFilename;
try
{
expressionEvaluator.addExpressionSource( syspropExprSource );
actualFilename = expressionEvaluator.expand( this.logFilename );
}
catch ( EvaluatorException e1 )
{
actualFilename = this.logFilename;
}
this.logFile = new File( actualFilename );
File parentDir = logFile.getParentFile();
if ( parentDir != null )
{
if ( !parentDir.exists() )
{
parentDir.mkdirs();
}
}
if ( StringUtils.isBlank( timestampFormat ) )
{
timestampFormat = "yyyy-MM-dd HH:mm:ss";
}
timestamp = new SimpleDateFormat( timestampFormat );
try
{
writer = new PrintWriter( new FileWriter( logFile ) );
log( "Logging Initialized." );
}
catch ( IOException e )
{
throw new InitializationException( "Unable to initialize log file writer: " + logFile.getAbsolutePath(), e );
}
}
}

View File

@ -19,6 +19,7 @@ package org.apache.maven.archiva.web.repository;
* under the License.
*/
import org.apache.maven.archiva.common.utils.PathUtil;
import org.apache.maven.archiva.model.ArtifactReference;
import org.apache.maven.archiva.model.ProjectReference;
import org.apache.maven.archiva.model.VersionedReference;
@ -28,10 +29,14 @@ import org.apache.maven.archiva.repository.ManagedRepositoryContent;
import org.apache.maven.archiva.repository.RepositoryContentFactory;
import org.apache.maven.archiva.repository.RepositoryException;
import org.apache.maven.archiva.repository.RepositoryNotFoundException;
import org.apache.maven.archiva.repository.audit.AuditEvent;
import org.apache.maven.archiva.repository.audit.AuditListener;
import org.apache.maven.archiva.repository.audit.Auditable;
import org.apache.maven.archiva.repository.content.RepositoryRequest;
import org.apache.maven.archiva.repository.layout.LayoutException;
import org.apache.maven.archiva.repository.metadata.MetadataTools;
import org.apache.maven.archiva.repository.metadata.RepositoryMetadataException;
import org.apache.maven.archiva.security.ArchivaUser;
import org.apache.maven.model.DistributionManagement;
import org.apache.maven.model.Model;
import org.apache.maven.model.Relocation;
@ -49,6 +54,8 @@ import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
@ -64,12 +71,18 @@ import javax.servlet.http.HttpServletResponse;
*/
public class ProxiedDavServer
extends AbstractDavServerComponent
implements Auditable
{
/**
* @plexus.requirement role-hint="simple"
*/
private DavServerComponent davServer;
/**
* @plexus.requirement role="org.apache.maven.archiva.repository.audit.AuditListener"
*/
private List<AuditListener> auditListeners = new ArrayList<AuditListener>();
/**
* @plexus.requirement
*/
@ -90,6 +103,11 @@ public class ProxiedDavServer
*/
private MetadataTools metadataTools;
/**
* @plexus.requirement role-hint="xwork"
*/
private ArchivaUser archivaUser;
private ManagedRepositoryContent managedRepository;
public String getPrefix()
@ -136,11 +154,11 @@ public class ProxiedDavServer
{
boolean isGet = WebdavMethodUtil.isReadMethod( request.getRequest().getMethod() );
boolean isPut = WebdavMethodUtil.isWriteMethod( request.getRequest().getMethod() );
String resource = request.getLogicalResource();
if ( isGet )
{
// Default behaviour is to treat the resource natively.
String resource = request.getLogicalResource();
File resourceFile = new File( managedRepository.getRepoRoot(), resource );
// If this a directory resource, then we are likely browsing.
@ -173,8 +191,13 @@ public class ProxiedDavServer
// Adjust the pathInfo resource to be in the format that the dav server impl expects.
request.getRequest().setPathInfo( resource );
boolean previouslyExisted = resourceFile.exists();
// Attempt to fetch the resource from any defined proxy.
fetchContentFromProxies( request, resource );
if( fetchContentFromProxies( request, resource ) )
{
processAuditEvents( request, resource, previouslyExisted, resourceFile, " (proxied)" );
}
}
catch ( LayoutException e )
{
@ -217,12 +240,24 @@ public class ProxiedDavServer
File rootDirectory = getRootDirectory();
if ( rootDirectory != null )
{
new File( rootDirectory, request.getLogicalResource() ).getParentFile().mkdirs();
File destDir = new File( rootDirectory, resource ).getParentFile();
if( !destDir.exists() )
{
destDir.mkdirs();
String relPath = PathUtil.getRelative( rootDirectory.getAbsolutePath(), destDir );
triggerAuditEvent( request, relPath, AuditEvent.CREATE_DIR );
}
}
File resourceFile = new File( managedRepository.getRepoRoot(), resource );
boolean previouslyExisted = resourceFile.exists();
// Allow the dav server to process the put request.
davServer.process( request, response );
processAuditEvents( request, resource, previouslyExisted, resourceFile, null );
// All done.
return;
}
@ -277,7 +312,7 @@ public class ProxiedDavServer
}
}
private void fetchContentFromProxies( DavServerRequest request, String resource )
private boolean fetchContentFromProxies( DavServerRequest request, String resource )
throws ServletException
{
if ( repositoryRequest.isSupportFile( resource ) )
@ -285,16 +320,13 @@ public class ProxiedDavServer
// Checksums are fetched with artifact / metadata.
// Need to adjust the path for the checksum resource.
return;
return false;
}
// Is it a Metadata resource?
if ( repositoryRequest.isDefault( resource ) && repositoryRequest.isMetadata( resource ) )
{
if ( fetchMetadataFromProxies( request, resource ) )
{
return;
}
return fetchMetadataFromProxies( request, resource );
}
// Not any of the above? Then it's gotta be an artifact reference.
@ -307,11 +339,11 @@ public class ProxiedDavServer
{
applyServerSideRelocation( artifact );
connectors.fetchFromProxies( managedRepository, artifact );
File proxiedFile = connectors.fetchFromProxies( managedRepository, artifact );
// Set the path to the resource using managed repository specific layout format.
request.getRequest().setPathInfo( managedRepository.toPath( artifact ) );
return;
return ( proxiedFile != null );
}
}
catch ( LayoutException e )
@ -322,6 +354,7 @@ public class ProxiedDavServer
{
throw new ServletException( "Unable to fetch artifact resource.", e );
}
return false;
}
private boolean fetchMetadataFromProxies( DavServerRequest request, String resource )
@ -481,4 +514,82 @@ public class ProxiedDavServer
{
return managedRepository;
}
private void processAuditEvents( DavServerRequest request, String resource, boolean previouslyExisted,
File resourceFile, String suffix )
{
if( suffix == null )
{
suffix = "";
}
// Process Create Audit Events.
if ( !previouslyExisted && resourceFile.exists() )
{
if ( resourceFile.isFile() )
{
triggerAuditEvent( request, resource, AuditEvent.CREATE_FILE + suffix );
}
else if ( resourceFile.isDirectory() )
{
triggerAuditEvent( request, resource, AuditEvent.CREATE_DIR + suffix );
}
}
// Process Remove Audit Events.
else if ( previouslyExisted && !resourceFile.exists() )
{
if ( resourceFile.isFile() )
{
triggerAuditEvent( request, resource, AuditEvent.REMOVE_FILE + suffix );
}
else if ( resourceFile.isDirectory() )
{
triggerAuditEvent( request, resource, AuditEvent.REMOVE_DIR + suffix );
}
}
// Process modify events.
else
{
if ( resourceFile.isFile() )
{
triggerAuditEvent( request, resource, AuditEvent.MODIFY_FILE + suffix );
}
}
}
private void triggerAuditEvent( String user, String remoteIP, String resource, String action )
{
AuditEvent event = new AuditEvent( this.getPrefix(), user, resource, action );
event.setRemoteIP( remoteIP );
for ( AuditListener listener : auditListeners )
{
listener.auditEvent( event );
}
}
private void triggerAuditEvent( DavServerRequest request, String resource, String action )
{
triggerAuditEvent( archivaUser.getActivePrincipal(), getRemoteIP( request ), resource, action );
}
private String getRemoteIP( DavServerRequest request )
{
return request.getRequest().getRemoteAddr();
}
public void addAuditListener( AuditListener listener )
{
this.auditListeners.add( listener );
}
public void clearAuditListeners()
{
this.auditListeners.clear();
}
public void removeAuditListener( AuditListener listener )
{
this.auditListeners.remove( listener );
}
}

View File

@ -63,8 +63,6 @@ public class RepositoryServlet
private HttpAuthenticator httpAuth;
private AuditLog audit;
private ArchivaConfiguration configuration;
private Map<String, ManagedRepositoryConfiguration> repositoryMap;
@ -80,7 +78,6 @@ public class RepositoryServlet
securitySystem = (SecuritySystem) lookup( SecuritySystem.ROLE );
httpAuth = (HttpAuthenticator) lookup( HttpAuthenticator.ROLE, "basic" );
audit = (AuditLog) lookup( AuditLog.ROLE );
configuration = (ArchivaConfiguration) lookup( ArchivaConfiguration.class.getName() );
configuration.addListener( this );
@ -108,7 +105,6 @@ public class RepositoryServlet
DavServerComponent server = createServer( repo.getId(), repoDir, servletConfig );
server.setUseIndexHtml( true );
server.addListener( audit );
}
}
@ -132,14 +128,6 @@ public class RepositoryServlet
log( "Unable to release HttpAuth : " + e.getMessage(), e );
}
try
{
release( audit );
}
catch ( ServletException e )
{
log( "Unable to release AuditLog : " + e.getMessage(), e );
}
try
{
release( configuration );
}

View File

@ -12,6 +12,15 @@
</layout>
</appender>
<appender name="auditlog" class="org.apache.log4j.DailyRollingFileAppender">
<param name="file" value="${appserver.base}/logs/audit.log" />
<param name="append" value="true" />
<param name="datePattern" value="'.'yyyy-MM-dd" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d{yyyy-MM-dd HH:mm:ss} %m%n"/>
</layout>
</appender>
<appender name="console" class="org.apache.log4j.ConsoleAppender">
<param name="Target" value="System.out"/>
<layout class="org.apache.log4j.PatternLayout">
@ -28,6 +37,11 @@
<level value="debug" />
</logger>
<logger name="org.apache.archiva.AuditLog">
<level value="info" />
<appender-ref ref="auditlog" />
</logger>
<logger name="org.codehaus.plexus.security">
<level value="info"/>
</logger>