001/*
002 * Licensed to the Apache Software Foundation (ASF) under one
003 * or more contributor license agreements.  See the NOTICE file
004 * distributed with this work for additional information
005 * regarding copyright ownership.  The ASF licenses this file
006 * to you under the Apache License, Version 2.0 (the
007 * "License"); you may not use this file except in compliance
008 * with the License.  You may obtain a copy of the License at
009 *
010 *   http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing,
013 * software distributed under the License is distributed on an
014 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015 * KIND, either express or implied.  See the License for the
016 * specific language governing permissions and limitations
017 * under the License.
018 */
019package org.eclipse.aether.util.graph.manager;
020
021import java.util.Collection;
022
023import org.eclipse.aether.collection.DependencyManager;
024import org.eclipse.aether.graph.Exclusion;
025import org.eclipse.aether.scope.ScopeManager;
026import org.eclipse.aether.scope.SystemDependencyScope;
027
028/**
029 * A dependency manager that applies management at all levels with aggressive transitive behavior.
030 *
031 * <h2>Overview</h2>
032 * <p>
033 * This manager provides the most aggressive dependency management approach, applying management
034 * rules at every level of the dependency graph. Unlike other managers, it starts applying
035 * management from the very first level (depth=0) and continues indefinitely.
036 * </p>
037 *
038 * <h2>Key Characteristics</h2>
039 * <ul>
040 * <li><strong>Aggressive Application:</strong> {@code deriveUntil=Integer.MAX_VALUE}, {@code applyFrom=0}</li>
041 * <li><strong>First Level Management:</strong> Applies management even at the root level</li>
042 * <li><strong>ModelBuilder Interference:</strong> Ignores and overrides ModelBuilder's work</li>
043 * <li><strong>Complete Transitivity:</strong> Manages dependencies at all depths</li>
044 * </ul>
045 *
046 * <h2>When NOT to Use</h2>
047 * <p>
048 * <strong>⚠️ Warning:</strong> This manager is <em>not recommended for Maven or Maven-like use cases</em>
049 * because it interferes with ModelBuilder, potentially rewriting models that ModelBuilder has
050 * already processed correctly. This can lead to unexpected dependency resolution behavior.
051 * </p>
052 *
053 * <h2>When to Use</h2>
054 * <p>
055 * Consider this manager only for non-Maven scenarios where you need complete control over
056 * dependency management at all levels and are not using Maven's ModelBuilder.
057 * </p>
058 *
059 * <h2>Comparison with Other Managers</h2>
060 * <ul>
061 * <li>{@link ClassicDependencyManager}: Maven 2.x compatibility, limited scope</li>
062 * <li>{@link TransitiveDependencyManager}: Proper transitive management, ModelBuilder-friendly</li>
063 * <li><strong>This manager:</strong> Aggressive, all-level management (use with caution)</li>
064 * </ul>
065 *
066 * @author Christian Schulte
067 * @since 1.4.0
068 * @see ClassicDependencyManager
069 * @see TransitiveDependencyManager
070 */
071public final class DefaultDependencyManager extends AbstractDependencyManager {
072    /**
073     * Creates a new dependency manager without any management information.
074     */
075    public DefaultDependencyManager() {
076        this(null);
077    }
078
079    /**
080     * Creates a new dependency manager with aggressive management behavior.
081     * <p>
082     * <strong>⚠️ Warning:</strong> This manager is not recommended for Maven use cases.
083     * It initializes with the most aggressive settings:
084     * <ul>
085     * <li>deriveUntil = Integer.MAX_VALUE (always collect management rules)</li>
086     * <li>applyFrom = 0 (apply management from the very first level)</li>
087     * <li>No respect for ModelBuilder's work</li>
088     * </ul>
089     *
090     * @param scopeManager application-specific scope manager for handling system dependencies,
091     *                     may be null to use legacy system dependency scope handling
092     */
093    public DefaultDependencyManager(ScopeManager scopeManager) {
094        super(Integer.MAX_VALUE, 0, scopeManager);
095    }
096
097    @SuppressWarnings("checkstyle:ParameterNumber")
098    private DefaultDependencyManager(
099            AbstractDependencyManager parent,
100            int depth,
101            int deriveUntil,
102            int applyFrom,
103            MMap<Key, String> managedVersions,
104            MMap<Key, String> managedScopes,
105            MMap<Key, Boolean> managedOptionals,
106            MMap<Key, String> managedLocalPaths,
107            MMap<Key, Holder<Collection<Exclusion>>> managedExclusions,
108            SystemDependencyScope systemDependencyScope) {
109        super(
110                parent,
111                depth,
112                deriveUntil,
113                applyFrom,
114                managedVersions,
115                managedScopes,
116                managedOptionals,
117                managedLocalPaths,
118                managedExclusions,
119                systemDependencyScope);
120    }
121
122    @Override
123    protected DependencyManager newInstance(
124            MMap<Key, String> managedVersions,
125            MMap<Key, String> managedScopes,
126            MMap<Key, Boolean> managedOptionals,
127            MMap<Key, String> managedLocalPaths,
128            MMap<Key, Holder<Collection<Exclusion>>> managedExclusions) {
129        return new DefaultDependencyManager(
130                this,
131                depth + 1,
132                deriveUntil,
133                applyFrom,
134                managedVersions,
135                managedScopes,
136                managedOptionals,
137                managedLocalPaths,
138                managedExclusions,
139                systemDependencyScope);
140    }
141}