1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.eclipse.aether.internal.impl;
20
21 import javax.inject.Inject;
22 import javax.inject.Named;
23 import javax.inject.Singleton;
24
25 import java.util.ArrayList;
26 import java.util.Arrays;
27 import java.util.List;
28 import java.util.ListIterator;
29
30 import org.eclipse.aether.RepositoryCache;
31 import org.eclipse.aether.RepositorySystemSession;
32 import org.eclipse.aether.impl.RemoteRepositoryManager;
33 import org.eclipse.aether.impl.UpdatePolicyAnalyzer;
34 import org.eclipse.aether.repository.Authentication;
35 import org.eclipse.aether.repository.AuthenticationSelector;
36 import org.eclipse.aether.repository.MirrorSelector;
37 import org.eclipse.aether.repository.Proxy;
38 import org.eclipse.aether.repository.ProxySelector;
39 import org.eclipse.aether.repository.RemoteRepository;
40 import org.eclipse.aether.repository.RepositoryPolicy;
41 import org.eclipse.aether.spi.connector.checksum.ChecksumPolicyProvider;
42 import org.slf4j.Logger;
43 import org.slf4j.LoggerFactory;
44
45 import static java.util.Objects.requireNonNull;
46
47
48
49 @Singleton
50 @Named
51 public class DefaultRemoteRepositoryManager implements RemoteRepositoryManager {
52
53 private static final class LoggedMirror {
54
55 private final Object[] keys;
56
57 LoggedMirror(RemoteRepository original, RemoteRepository mirror) {
58 keys = new Object[] {mirror.getId(), mirror.getUrl(), original.getId(), original.getUrl()};
59 }
60
61 @Override
62 public boolean equals(Object obj) {
63 if (this == obj) {
64 return true;
65 } else if (!(obj instanceof LoggedMirror)) {
66 return false;
67 }
68 LoggedMirror that = (LoggedMirror) obj;
69 return Arrays.equals(keys, that.keys);
70 }
71
72 @Override
73 public int hashCode() {
74 return Arrays.hashCode(keys);
75 }
76 }
77
78 private static final Logger LOGGER = LoggerFactory.getLogger(DefaultRemoteRepositoryManager.class);
79
80 private final UpdatePolicyAnalyzer updatePolicyAnalyzer;
81
82 private final ChecksumPolicyProvider checksumPolicyProvider;
83
84 @Inject
85 public DefaultRemoteRepositoryManager(
86 UpdatePolicyAnalyzer updatePolicyAnalyzer, ChecksumPolicyProvider checksumPolicyProvider) {
87 this.updatePolicyAnalyzer = requireNonNull(updatePolicyAnalyzer, "update policy analyzer cannot be null");
88 this.checksumPolicyProvider = requireNonNull(checksumPolicyProvider, "checksum policy provider cannot be null");
89 }
90
91 @Override
92 public List<RemoteRepository> aggregateRepositories(
93 RepositorySystemSession session,
94 List<RemoteRepository> dominantRepositories,
95 List<RemoteRepository> recessiveRepositories,
96 boolean recessiveIsRaw) {
97 requireNonNull(session, "session cannot be null");
98 requireNonNull(dominantRepositories, "dominantRepositories cannot be null");
99 requireNonNull(recessiveRepositories, "recessiveRepositories cannot be null");
100 if (recessiveRepositories.isEmpty()) {
101 return dominantRepositories;
102 }
103
104 MirrorSelector mirrorSelector = session.getMirrorSelector();
105 AuthenticationSelector authSelector = session.getAuthenticationSelector();
106 ProxySelector proxySelector = session.getProxySelector();
107
108 List<RemoteRepository> result = new ArrayList<>(dominantRepositories);
109
110 next:
111 for (RemoteRepository recessiveRepository : recessiveRepositories) {
112 RemoteRepository repository = recessiveRepository;
113
114 if (recessiveIsRaw) {
115 RemoteRepository mirrorRepository = mirrorSelector.getMirror(recessiveRepository);
116
117 if (mirrorRepository != null) {
118 logMirror(session, recessiveRepository, mirrorRepository);
119 repository = mirrorRepository;
120 }
121 }
122
123 String key = getKey(repository);
124
125 for (ListIterator<RemoteRepository> it = result.listIterator(); it.hasNext(); ) {
126 RemoteRepository dominantRepository = it.next();
127
128 if (key.equals(getKey(dominantRepository))) {
129 if (!dominantRepository.getMirroredRepositories().isEmpty()
130 && !repository.getMirroredRepositories().isEmpty()) {
131 RemoteRepository mergedRepository = mergeMirrors(session, dominantRepository, repository);
132 if (mergedRepository != dominantRepository) {
133 it.set(mergedRepository);
134 }
135 }
136
137 continue next;
138 }
139 }
140
141 if (recessiveIsRaw) {
142 RemoteRepository.Builder builder = null;
143 Authentication auth = authSelector.getAuthentication(repository);
144 if (auth != null) {
145 builder = new RemoteRepository.Builder(repository);
146 builder.setAuthentication(auth);
147 }
148 Proxy proxy = proxySelector.getProxy(repository);
149 if (proxy != null) {
150 if (builder == null) {
151 builder = new RemoteRepository.Builder(repository);
152 }
153 builder.setProxy(proxy);
154 }
155 if (builder != null) {
156 repository = builder.build();
157 }
158 }
159
160 result.add(repository);
161 }
162
163 return result;
164 }
165
166 private void logMirror(RepositorySystemSession session, RemoteRepository original, RemoteRepository mirror) {
167 if (!LOGGER.isDebugEnabled()) {
168 return;
169 }
170 RepositoryCache cache = session.getCache();
171 if (cache != null) {
172 Object key = new LoggedMirror(original, mirror);
173 if (cache.get(session, key) != null) {
174 return;
175 }
176 cache.put(session, key, Boolean.TRUE);
177 }
178 LOGGER.debug(
179 "Using mirror {} ({}) for {} ({}).",
180 mirror.getId(),
181 mirror.getUrl(),
182 original.getId(),
183 original.getUrl());
184 }
185
186 private String getKey(RemoteRepository repository) {
187 return repository.getId();
188 }
189
190 private RemoteRepository mergeMirrors(
191 RepositorySystemSession session, RemoteRepository dominant, RemoteRepository recessive) {
192 RemoteRepository.Builder merged = null;
193 RepositoryPolicy releases = null, snapshots = null;
194
195 next:
196 for (RemoteRepository rec : recessive.getMirroredRepositories()) {
197 String recKey = getKey(rec);
198
199 for (RemoteRepository dom : dominant.getMirroredRepositories()) {
200 if (recKey.equals(getKey(dom))) {
201 continue next;
202 }
203 }
204
205 if (merged == null) {
206 merged = new RemoteRepository.Builder(dominant);
207 releases = dominant.getPolicy(false);
208 snapshots = dominant.getPolicy(true);
209 }
210
211 releases = merge(session, releases, rec.getPolicy(false), false);
212 snapshots = merge(session, snapshots, rec.getPolicy(true), false);
213
214 merged.addMirroredRepository(rec);
215 }
216
217 if (merged == null) {
218 return dominant;
219 }
220 return merged.setReleasePolicy(releases).setSnapshotPolicy(snapshots).build();
221 }
222
223 @Override
224 public RepositoryPolicy getPolicy(
225 RepositorySystemSession session, RemoteRepository repository, boolean releases, boolean snapshots) {
226 requireNonNull(session, "session cannot be null");
227 requireNonNull(repository, "repository cannot be null");
228 RepositoryPolicy policy1 = releases ? repository.getPolicy(false) : null;
229 RepositoryPolicy policy2 = snapshots ? repository.getPolicy(true) : null;
230 return merge(session, policy1, policy2, true);
231 }
232
233 private RepositoryPolicy merge(
234 RepositorySystemSession session, RepositoryPolicy policy1, RepositoryPolicy policy2, boolean globalPolicy) {
235 RepositoryPolicy policy;
236
237 if (policy2 == null) {
238 if (globalPolicy) {
239 policy = merge(
240 policy1,
241 session.getArtifactUpdatePolicy(),
242 session.getMetadataUpdatePolicy(),
243 session.getChecksumPolicy());
244 } else {
245 policy = policy1;
246 }
247 } else if (policy1 == null) {
248 if (globalPolicy) {
249 policy = merge(
250 policy2,
251 session.getArtifactUpdatePolicy(),
252 session.getMetadataUpdatePolicy(),
253 session.getChecksumPolicy());
254 } else {
255 policy = policy2;
256 }
257 } else if (!policy2.isEnabled()) {
258 if (globalPolicy) {
259 policy = merge(
260 policy1,
261 session.getArtifactUpdatePolicy(),
262 session.getMetadataUpdatePolicy(),
263 session.getChecksumPolicy());
264 } else {
265 policy = policy1;
266 }
267 } else if (!policy1.isEnabled()) {
268 if (globalPolicy) {
269 policy = merge(
270 policy2,
271 session.getArtifactUpdatePolicy(),
272 session.getMetadataUpdatePolicy(),
273 session.getChecksumPolicy());
274 } else {
275 policy = policy2;
276 }
277 } else {
278 String checksums = session.getChecksumPolicy();
279
280 if (globalPolicy && checksums != null && !checksums.isEmpty()) {
281
282 } else {
283 checksums = checksumPolicyProvider.getEffectiveChecksumPolicy(
284 session, policy1.getChecksumPolicy(), policy2.getChecksumPolicy());
285 }
286
287 String artifactUpdates = session.getArtifactUpdatePolicy();
288
289 if (globalPolicy && artifactUpdates != null && !artifactUpdates.isEmpty()) {
290
291 } else {
292 artifactUpdates = updatePolicyAnalyzer.getEffectiveUpdatePolicy(
293 session, policy1.getArtifactUpdatePolicy(), policy2.getArtifactUpdatePolicy());
294 }
295 String metadataUpdates = session.getMetadataUpdatePolicy();
296 if (globalPolicy && metadataUpdates != null && !metadataUpdates.isEmpty()) {
297
298 } else {
299 metadataUpdates = updatePolicyAnalyzer.getEffectiveUpdatePolicy(
300 session, policy1.getMetadataUpdatePolicy(), policy2.getMetadataUpdatePolicy());
301 }
302
303 policy = new RepositoryPolicy(true, artifactUpdates, metadataUpdates, checksums);
304 }
305
306 return policy;
307 }
308
309 private RepositoryPolicy merge(
310 RepositoryPolicy policy, String artifactUpdates, String metadataUpdates, String checksums) {
311 if (policy != null) {
312 if (artifactUpdates == null || artifactUpdates.isEmpty()) {
313 artifactUpdates = policy.getArtifactUpdatePolicy();
314 }
315 if (metadataUpdates == null || metadataUpdates.isEmpty()) {
316 metadataUpdates = policy.getMetadataUpdatePolicy();
317 }
318 if (checksums == null || checksums.isEmpty()) {
319 checksums = policy.getChecksumPolicy();
320 }
321 if (!policy.getArtifactUpdatePolicy().equals(artifactUpdates)
322 || !policy.getMetadataUpdatePolicy().equals(metadataUpdates)
323 || !policy.getChecksumPolicy().equals(checksums)) {
324 policy = new RepositoryPolicy(policy.isEnabled(), artifactUpdates, metadataUpdates, checksums);
325 }
326 }
327 return policy;
328 }
329 }