1 package org.eclipse.aether.impl;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import java.lang.reflect.Constructor;
23 import java.lang.reflect.Modifier;
24 import java.util.ArrayList;
25 import java.util.Collection;
26 import java.util.Collections;
27 import java.util.HashMap;
28 import java.util.LinkedHashSet;
29 import java.util.List;
30 import java.util.Map;
31 import static java.util.Objects.requireNonNull;
32
33 import org.eclipse.aether.RepositorySystem;
34 import org.eclipse.aether.internal.impl.DefaultArtifactResolver;
35 import org.eclipse.aether.internal.impl.DefaultChecksumPolicyProvider;
36 import org.eclipse.aether.internal.impl.DefaultTrackingFileManager;
37 import org.eclipse.aether.internal.impl.TrackingFileManager;
38 import org.eclipse.aether.internal.impl.collect.DefaultDependencyCollector;
39 import org.eclipse.aether.internal.impl.DefaultDeployer;
40 import org.eclipse.aether.internal.impl.DefaultFileProcessor;
41 import org.eclipse.aether.internal.impl.DefaultInstaller;
42 import org.eclipse.aether.internal.impl.DefaultLocalRepositoryProvider;
43 import org.eclipse.aether.internal.impl.DefaultMetadataResolver;
44 import org.eclipse.aether.internal.impl.DefaultOfflineController;
45 import org.eclipse.aether.internal.impl.DefaultRemoteRepositoryManager;
46 import org.eclipse.aether.internal.impl.DefaultRepositoryConnectorProvider;
47 import org.eclipse.aether.internal.impl.DefaultRepositoryEventDispatcher;
48 import org.eclipse.aether.internal.impl.DefaultRepositoryLayoutProvider;
49 import org.eclipse.aether.internal.impl.DefaultRepositorySystem;
50 import org.eclipse.aether.internal.impl.DefaultTransporterProvider;
51 import org.eclipse.aether.internal.impl.DefaultUpdateCheckManager;
52 import org.eclipse.aether.internal.impl.DefaultUpdatePolicyAnalyzer;
53 import org.eclipse.aether.internal.impl.EnhancedLocalRepositoryManagerFactory;
54 import org.eclipse.aether.internal.impl.Maven2RepositoryLayoutFactory;
55 import org.eclipse.aether.internal.impl.SimpleLocalRepositoryManagerFactory;
56 import org.eclipse.aether.internal.impl.slf4j.Slf4jLoggerFactory;
57 import org.eclipse.aether.internal.impl.synccontext.DefaultSyncContextFactory;
58 import org.eclipse.aether.internal.impl.synccontext.NamedLockFactorySelector;
59 import org.eclipse.aether.spi.connector.checksum.ChecksumPolicyProvider;
60 import org.eclipse.aether.spi.connector.layout.RepositoryLayoutFactory;
61 import org.eclipse.aether.spi.connector.layout.RepositoryLayoutProvider;
62 import org.eclipse.aether.spi.connector.transport.TransporterProvider;
63 import org.eclipse.aether.spi.io.FileProcessor;
64 import org.eclipse.aether.spi.localrepo.LocalRepositoryManagerFactory;
65 import org.eclipse.aether.spi.locator.Service;
66 import org.eclipse.aether.spi.locator.ServiceLocator;
67 import org.eclipse.aether.spi.log.LoggerFactory;
68 import org.eclipse.aether.spi.synccontext.SyncContextFactory;
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85 @Deprecated
86 public final class DefaultServiceLocator
87 implements ServiceLocator
88 {
89
90 private class Entry<T>
91 {
92
93 private final Class<T> type;
94
95 private final Collection<Object> providers;
96
97 private List<T> instances;
98
99 Entry( Class<T> type )
100 {
101 this.type = requireNonNull( type, "service type cannot be null" );
102 providers = new LinkedHashSet<>( 8 );
103 }
104
105 public synchronized void setServices( T... services )
106 {
107 providers.clear();
108 if ( services != null )
109 {
110 for ( T service : services )
111 {
112 providers.add( requireNonNull( service, "service instance cannot be null" ) );
113 }
114 }
115 instances = null;
116 }
117
118 public synchronized void setService( Class<? extends T> impl )
119 {
120 providers.clear();
121 addService( impl );
122 }
123
124 public synchronized void addService( Class<? extends T> impl )
125 {
126 providers.add( requireNonNull( impl, "implementation class cannot be null" ) );
127 instances = null;
128 }
129
130 public T getInstance()
131 {
132 List<T> instances = getInstances();
133 return instances.isEmpty() ? null : instances.get( 0 );
134 }
135
136 public synchronized List<T> getInstances()
137 {
138 if ( instances == null )
139 {
140 instances = new ArrayList<>( providers.size() );
141 for ( Object provider : providers )
142 {
143 T instance;
144 if ( provider instanceof Class )
145 {
146 instance = newInstance( (Class<?>) provider );
147 }
148 else
149 {
150 instance = type.cast( provider );
151 }
152 if ( instance != null )
153 {
154 instances.add( instance );
155 }
156 }
157 instances = Collections.unmodifiableList( instances );
158 }
159 return instances;
160 }
161
162 private T newInstance( Class<?> impl )
163 {
164 try
165 {
166 Constructor<?> constr = impl.getDeclaredConstructor();
167 if ( !Modifier.isPublic( constr.getModifiers() ) )
168 {
169 constr.setAccessible( true );
170 }
171 Object obj = constr.newInstance();
172
173 T instance = type.cast( obj );
174 if ( instance instanceof Service )
175 {
176 ( (Service) instance ).initService( DefaultServiceLocator.this );
177 }
178 return instance;
179 }
180 catch ( Exception | LinkageError e )
181 {
182 serviceCreationFailed( type, impl, e );
183 }
184 return null;
185 }
186
187 }
188
189 private final Map<Class<?>, Entry<?>> entries;
190
191 private ErrorHandler errorHandler;
192
193
194
195
196 public DefaultServiceLocator()
197 {
198 entries = new HashMap<>();
199
200 addService( RepositorySystem.class, DefaultRepositorySystem.class );
201 addService( ArtifactResolver.class, DefaultArtifactResolver.class );
202 addService( DependencyCollector.class, DefaultDependencyCollector.class );
203 addService( Deployer.class, DefaultDeployer.class );
204 addService( Installer.class, DefaultInstaller.class );
205 addService( MetadataResolver.class, DefaultMetadataResolver.class );
206 addService( RepositoryLayoutProvider.class, DefaultRepositoryLayoutProvider.class );
207 addService( RepositoryLayoutFactory.class, Maven2RepositoryLayoutFactory.class );
208 addService( TransporterProvider.class, DefaultTransporterProvider.class );
209 addService( ChecksumPolicyProvider.class, DefaultChecksumPolicyProvider.class );
210 addService( RepositoryConnectorProvider.class, DefaultRepositoryConnectorProvider.class );
211 addService( RemoteRepositoryManager.class, DefaultRemoteRepositoryManager.class );
212 addService( UpdateCheckManager.class, DefaultUpdateCheckManager.class );
213 addService( UpdatePolicyAnalyzer.class, DefaultUpdatePolicyAnalyzer.class );
214 addService( FileProcessor.class, DefaultFileProcessor.class );
215 addService( org.eclipse.aether.impl.SyncContextFactory.class,
216 org.eclipse.aether.internal.impl.synccontext.legacy.DefaultSyncContextFactory.class );
217 addService( SyncContextFactory.class, DefaultSyncContextFactory.class );
218 addService( RepositoryEventDispatcher.class, DefaultRepositoryEventDispatcher.class );
219 addService( OfflineController.class, DefaultOfflineController.class );
220 addService( LocalRepositoryProvider.class, DefaultLocalRepositoryProvider.class );
221 addService( LocalRepositoryManagerFactory.class, SimpleLocalRepositoryManagerFactory.class );
222 addService( LocalRepositoryManagerFactory.class, EnhancedLocalRepositoryManagerFactory.class );
223 addService( LoggerFactory.class, Slf4jLoggerFactory.class );
224 addService( TrackingFileManager.class, DefaultTrackingFileManager.class );
225 addService( NamedLockFactorySelector.class, NamedLockFactorySelector.class );
226 }
227
228 private <T> Entry<T> getEntry( Class<T> type, boolean create )
229 {
230 @SuppressWarnings( "unchecked" )
231 Entry<T> entry = (Entry<T>) entries.get( requireNonNull( type, "service type cannot be null" ) );
232 if ( entry == null && create )
233 {
234 entry = new Entry<>( type );
235 entries.put( type, entry );
236 }
237 return entry;
238 }
239
240
241
242
243
244
245
246
247
248
249
250 public <T> DefaultServiceLocator setService( Class<T> type, Class<? extends T> impl )
251 {
252 getEntry( type, true ).setService( impl );
253 return this;
254 }
255
256
257
258
259
260
261
262
263
264
265
266 public <T> DefaultServiceLocator addService( Class<T> type, Class<? extends T> impl )
267 {
268 getEntry( type, true ).addService( impl );
269 return this;
270 }
271
272
273
274
275
276
277
278
279
280 public <T> DefaultServiceLocator setServices( Class<T> type, T... services )
281 {
282 getEntry( type, true ).setServices( services );
283 return this;
284 }
285
286 public <T> T getService( Class<T> type )
287 {
288 Entry<T> entry = getEntry( type, false );
289 return ( entry != null ) ? entry.getInstance() : null;
290 }
291
292 public <T> List<T> getServices( Class<T> type )
293 {
294 Entry<T> entry = getEntry( type, false );
295 return ( entry != null ) ? entry.getInstances() : null;
296 }
297
298 private void serviceCreationFailed( Class<?> type, Class<?> impl, Throwable exception )
299 {
300 if ( errorHandler != null )
301 {
302 errorHandler.serviceCreationFailed( type, impl, exception );
303 }
304 }
305
306
307
308
309
310
311 public void setErrorHandler( ErrorHandler errorHandler )
312 {
313 this.errorHandler = errorHandler;
314 }
315
316
317
318
319 public abstract static class ErrorHandler
320 {
321
322
323
324
325
326
327
328
329
330 public void serviceCreationFailed( Class<?> type, Class<?> impl, Throwable exception )
331 {
332 }
333
334 }
335
336 }