package org.eclipse.aether;

/*
 * 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.
 */

/**
 * A listener being notified of events from the repository system. In general, the system sends events upon termination
 * of an operation like {@link #artifactResolved(RepositoryEvent)} regardless whether it succeeded or failed so
 * listeners need to inspect the event details carefully. Also, the listener may be called from an arbitrary thread.
 * <em>Note:</em> Implementors are strongly advised to inherit from {@link AbstractRepositoryListener} instead of
 * directly implementing this interface.
 * 
 * @see org.eclipse.aether.RepositorySystemSession#getRepositoryListener()
 * @see org.eclipse.aether.transfer.TransferListener
 * @noimplement This interface is not intended to be implemented by clients.
 * @noextend This interface is not intended to be extended by clients.
 */
public interface RepositoryListener
{

    /**
     * Notifies the listener of a syntactically or semantically invalid artifact descriptor.
     * {@link RepositoryEvent#getArtifact()} indicates the artifact whose descriptor is invalid and
     * {@link RepositoryEvent#getExceptions()} carries the encountered errors. Depending on the session's
     * {@link org.eclipse.aether.resolution.ArtifactDescriptorPolicy}, the underlying repository operation might abort
     * with an exception or ignore the invalid descriptor.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDescriptorInvalid( RepositoryEvent event );

    /**
     * Notifies the listener of a missing artifact descriptor. {@link RepositoryEvent#getArtifact()} indicates the
     * artifact whose descriptor is missing. Depending on the session's
     * {@link org.eclipse.aether.resolution.ArtifactDescriptorPolicy}, the underlying repository operation might abort
     * with an exception or ignore the missing descriptor.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDescriptorMissing( RepositoryEvent event );

    /**
     * Notifies the listener of syntactically or semantically invalid metadata. {@link RepositoryEvent#getMetadata()}
     * indicates the invalid metadata and {@link RepositoryEvent#getExceptions()} carries the encountered errors. The
     * underlying repository operation might still succeed, depending on whether the metadata in question is actually
     * needed to carry out the resolution process.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataInvalid( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact that is about to be resolved. {@link RepositoryEvent#getArtifact()} denotes
     * the artifact in question. Unlike the {@link #artifactDownloading(RepositoryEvent)} event, this event is fired
     * regardless whether the artifact already exists locally or not.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactResolving( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact whose resolution has been completed, either successfully or not.
     * {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the resolution succeeded or failed. Unlike the
     * {@link #artifactDownloaded(RepositoryEvent)} event, this event is fired regardless whether the artifact already
     * exists locally or not.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactResolved( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata that is about to be resolved. {@link RepositoryEvent#getMetadata()}
     * denotes the metadata in question. Unlike the {@link #metadataDownloading(RepositoryEvent)} event, this event is
     * fired regardless whether the metadata already exists locally or not.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataResolving( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata whose resolution has been completed, either successfully or not.
     * {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the resolution succeeded or failed. Unlike the
     * {@link #metadataDownloaded(RepositoryEvent)} event, this event is fired regardless whether the metadata already
     * exists locally or not.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataResolved( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact that is about to be downloaded from a remote repository.
     * {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getRepository()} the source repository. Unlike the
     * {@link #artifactResolving(RepositoryEvent)} event, this event is only fired when the artifact does not already
     * exist locally.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDownloading( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact whose download has been completed, either successfully or not.
     * {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the download succeeded or failed. Unlike the
     * {@link #artifactResolved(RepositoryEvent)} event, this event is only fired when the artifact does not already
     * exist locally.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDownloaded( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata that is about to be downloaded from a remote repository.
     * {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getRepository()} the source repository. Unlike the
     * {@link #metadataResolving(RepositoryEvent)} event, this event is only fired when the metadata does not already
     * exist locally.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataDownloading( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata whose download has been completed, either successfully or not.
     * {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the download succeeded or failed. Unlike the
     * {@link #metadataResolved(RepositoryEvent)} event, this event is only fired when the metadata does not already
     * exist locally.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataDownloaded( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact that is about to be installed to the local repository.
     * {@link RepositoryEvent#getArtifact()} denotes the artifact in question.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactInstalling( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact whose installation to the local repository has been completed, either
     * successfully or not. {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the installation succeeded or failed.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactInstalled( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata that is about to be installed to the local repository.
     * {@link RepositoryEvent#getMetadata()} denotes the metadata in question.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataInstalling( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata whose installation to the local repository has been completed, either
     * successfully or not. {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the installation succeeded or failed.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataInstalled( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact that is about to be uploaded to a remote repository.
     * {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getRepository()} the destination repository.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDeploying( RepositoryEvent event );

    /**
     * Notifies the listener of an artifact whose upload to a remote repository has been completed, either successfully
     * or not. {@link RepositoryEvent#getArtifact()} denotes the artifact in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the upload succeeded or failed.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void artifactDeployed( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata that is about to be uploaded to a remote repository.
     * {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getRepository()} the destination repository.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataDeploying( RepositoryEvent event );

    /**
     * Notifies the listener of some metadata whose upload to a remote repository has been completed, either
     * successfully or not. {@link RepositoryEvent#getMetadata()} denotes the metadata in question and
     * {@link RepositoryEvent#getExceptions()} indicates whether the upload succeeded or failed.
     * 
     * @param event The event details, must not be {@code null}.
     */
    void metadataDeployed( RepositoryEvent event );

}
