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; 020 021import java.util.Collections; 022import java.util.HashMap; 023import java.util.Map; 024 025import org.eclipse.aether.artifact.ArtifactType; 026import org.eclipse.aether.artifact.ArtifactTypeRegistry; 027import org.eclipse.aether.collection.DependencyGraphTransformer; 028import org.eclipse.aether.collection.DependencyManager; 029import org.eclipse.aether.collection.DependencySelector; 030import org.eclipse.aether.collection.DependencyTraverser; 031import org.eclipse.aether.collection.VersionFilter; 032import org.eclipse.aether.repository.Authentication; 033import org.eclipse.aether.repository.AuthenticationSelector; 034import org.eclipse.aether.repository.LocalRepository; 035import org.eclipse.aether.repository.LocalRepositoryManager; 036import org.eclipse.aether.repository.MirrorSelector; 037import org.eclipse.aether.repository.Proxy; 038import org.eclipse.aether.repository.ProxySelector; 039import org.eclipse.aether.repository.RemoteRepository; 040import org.eclipse.aether.repository.RepositoryPolicy; 041import org.eclipse.aether.repository.WorkspaceReader; 042import org.eclipse.aether.resolution.ArtifactDescriptorPolicy; 043import org.eclipse.aether.resolution.ResolutionErrorPolicy; 044import org.eclipse.aether.transfer.TransferListener; 045 046import static java.util.Objects.requireNonNull; 047 048/** 049 * A simple repository system session. 050 * <p> 051 * <strong>Note:</strong> This class is not thread-safe. It is assumed that the mutators get only called during an 052 * initialization phase and that the session itself is not changed once initialized and being used by the repository 053 * system. It is recommended to call {@link #setReadOnly()} once the session has been fully initialized to prevent 054 * accidental manipulation of it afterwards. 055 */ 056public final class DefaultRepositorySystemSession implements RepositorySystemSession { 057 058 private boolean readOnly; 059 060 private boolean offline; 061 062 private boolean ignoreArtifactDescriptorRepositories; 063 064 private ResolutionErrorPolicy resolutionErrorPolicy; 065 066 private ArtifactDescriptorPolicy artifactDescriptorPolicy; 067 068 private String checksumPolicy; 069 070 private String artifactUpdatePolicy; 071 072 private String metadataUpdatePolicy; 073 074 private LocalRepositoryManager localRepositoryManager; 075 076 private WorkspaceReader workspaceReader; 077 078 private RepositoryListener repositoryListener; 079 080 private TransferListener transferListener; 081 082 private Map<String, String> systemProperties; 083 084 private Map<String, String> systemPropertiesView; 085 086 private Map<String, String> userProperties; 087 088 private Map<String, String> userPropertiesView; 089 090 private Map<String, Object> configProperties; 091 092 private Map<String, Object> configPropertiesView; 093 094 private MirrorSelector mirrorSelector; 095 096 private ProxySelector proxySelector; 097 098 private AuthenticationSelector authenticationSelector; 099 100 private ArtifactTypeRegistry artifactTypeRegistry; 101 102 private DependencyTraverser dependencyTraverser; 103 104 private DependencyManager dependencyManager; 105 106 private DependencySelector dependencySelector; 107 108 private VersionFilter versionFilter; 109 110 private DependencyGraphTransformer dependencyGraphTransformer; 111 112 private SessionData data; 113 114 private RepositoryCache cache; 115 116 /** 117 * Creates an uninitialized session. <em>Note:</em> The new session is not ready to use, as a bare minimum, 118 * {@link #setLocalRepositoryManager(LocalRepositoryManager)} needs to be called but usually other settings also 119 * need to be customized to achieve meaningful behavior. 120 */ 121 public DefaultRepositorySystemSession() { 122 systemProperties = new HashMap<>(); 123 systemPropertiesView = Collections.unmodifiableMap(systemProperties); 124 userProperties = new HashMap<>(); 125 userPropertiesView = Collections.unmodifiableMap(userProperties); 126 configProperties = new HashMap<>(); 127 configPropertiesView = Collections.unmodifiableMap(configProperties); 128 mirrorSelector = NullMirrorSelector.INSTANCE; 129 proxySelector = NullProxySelector.INSTANCE; 130 authenticationSelector = NullAuthenticationSelector.INSTANCE; 131 artifactTypeRegistry = NullArtifactTypeRegistry.INSTANCE; 132 data = new DefaultSessionData(); 133 } 134 135 /** 136 * Creates a shallow copy of the specified session. Actually, the copy is not completely shallow, all maps holding 137 * system/user/config properties are copied as well. In other words, invoking any mutator on the new session itself 138 * has no effect on the original session. Other mutable objects like the session data and cache (if any) are not 139 * copied and will be shared with the original session unless reconfigured. 140 * 141 * @param session The session to copy, must not be {@code null}. 142 */ 143 public DefaultRepositorySystemSession(RepositorySystemSession session) { 144 requireNonNull(session, "repository system session cannot be null"); 145 146 setOffline(session.isOffline()); 147 setIgnoreArtifactDescriptorRepositories(session.isIgnoreArtifactDescriptorRepositories()); 148 setResolutionErrorPolicy(session.getResolutionErrorPolicy()); 149 setArtifactDescriptorPolicy(session.getArtifactDescriptorPolicy()); 150 setChecksumPolicy(session.getChecksumPolicy()); 151 setUpdatePolicy(session.getUpdatePolicy()); 152 setMetadataUpdatePolicy(session.getMetadataUpdatePolicy()); 153 setLocalRepositoryManager(session.getLocalRepositoryManager()); 154 setWorkspaceReader(session.getWorkspaceReader()); 155 setRepositoryListener(session.getRepositoryListener()); 156 setTransferListener(session.getTransferListener()); 157 setSystemProperties(session.getSystemProperties()); 158 setUserProperties(session.getUserProperties()); 159 setConfigProperties(session.getConfigProperties()); 160 setMirrorSelector(session.getMirrorSelector()); 161 setProxySelector(session.getProxySelector()); 162 setAuthenticationSelector(session.getAuthenticationSelector()); 163 setArtifactTypeRegistry(session.getArtifactTypeRegistry()); 164 setDependencyTraverser(session.getDependencyTraverser()); 165 setDependencyManager(session.getDependencyManager()); 166 setDependencySelector(session.getDependencySelector()); 167 setVersionFilter(session.getVersionFilter()); 168 setDependencyGraphTransformer(session.getDependencyGraphTransformer()); 169 setData(session.getData()); 170 setCache(session.getCache()); 171 } 172 173 @Override 174 public boolean isOffline() { 175 return offline; 176 } 177 178 /** 179 * Controls whether the repository system operates in offline mode and avoids/refuses any access to remote 180 * repositories. 181 * 182 * @param offline {@code true} if the repository system is in offline mode, {@code false} otherwise. 183 * @return This session for chaining, never {@code null}. 184 */ 185 public DefaultRepositorySystemSession setOffline(boolean offline) { 186 verifyStateForMutation(); 187 this.offline = offline; 188 return this; 189 } 190 191 @Override 192 public boolean isIgnoreArtifactDescriptorRepositories() { 193 return ignoreArtifactDescriptorRepositories; 194 } 195 196 /** 197 * Controls whether repositories declared in artifact descriptors should be ignored during transitive dependency 198 * collection. If enabled, only the repositories originally provided with the collect request will be considered. 199 * 200 * @param ignoreArtifactDescriptorRepositories {@code true} to ignore additional repositories from artifact 201 * descriptors, {@code false} to merge those with the originally 202 * specified repositories. 203 * @return This session for chaining, never {@code null}. 204 */ 205 public DefaultRepositorySystemSession setIgnoreArtifactDescriptorRepositories( 206 boolean ignoreArtifactDescriptorRepositories) { 207 verifyStateForMutation(); 208 this.ignoreArtifactDescriptorRepositories = ignoreArtifactDescriptorRepositories; 209 return this; 210 } 211 212 @Override 213 public ResolutionErrorPolicy getResolutionErrorPolicy() { 214 return resolutionErrorPolicy; 215 } 216 217 /** 218 * Sets the policy which controls whether resolutions errors from remote repositories should be cached. 219 * 220 * @param resolutionErrorPolicy The resolution error policy for this session, may be {@code null} if resolution 221 * errors should generally not be cached. 222 * @return This session for chaining, never {@code null}. 223 */ 224 public DefaultRepositorySystemSession setResolutionErrorPolicy(ResolutionErrorPolicy resolutionErrorPolicy) { 225 verifyStateForMutation(); 226 this.resolutionErrorPolicy = resolutionErrorPolicy; 227 return this; 228 } 229 230 @Override 231 public ArtifactDescriptorPolicy getArtifactDescriptorPolicy() { 232 return artifactDescriptorPolicy; 233 } 234 235 /** 236 * Sets the policy which controls how errors related to reading artifact descriptors should be handled. 237 * 238 * @param artifactDescriptorPolicy The descriptor error policy for this session, may be {@code null} if descriptor 239 * errors should generally not be tolerated. 240 * @return This session for chaining, never {@code null}. 241 */ 242 public DefaultRepositorySystemSession setArtifactDescriptorPolicy( 243 ArtifactDescriptorPolicy artifactDescriptorPolicy) { 244 verifyStateForMutation(); 245 this.artifactDescriptorPolicy = artifactDescriptorPolicy; 246 return this; 247 } 248 249 @Override 250 public String getChecksumPolicy() { 251 return checksumPolicy; 252 } 253 254 /** 255 * Sets the global checksum policy. If set, the global checksum policy overrides the checksum policies of the remote 256 * repositories being used for resolution. 257 * 258 * @param checksumPolicy The global checksum policy, may be {@code null}/empty to apply the per-repository policies. 259 * @return This session for chaining, never {@code null}. 260 * @see RepositoryPolicy#CHECKSUM_POLICY_FAIL 261 * @see RepositoryPolicy#CHECKSUM_POLICY_IGNORE 262 * @see RepositoryPolicy#CHECKSUM_POLICY_WARN 263 */ 264 public DefaultRepositorySystemSession setChecksumPolicy(String checksumPolicy) { 265 verifyStateForMutation(); 266 this.checksumPolicy = checksumPolicy; 267 return this; 268 } 269 270 @Override 271 public String getUpdatePolicy() { 272 return getArtifactUpdatePolicy(); 273 } 274 275 /** 276 * Sets the global update policy. If set, the global update policy overrides the update policies of the remote 277 * repositories being used for resolution. 278 * <p> 279 * This method is meant for code that does not want to distinguish between artifact and metadata policies. 280 * Note: applications should either use get/set updatePolicy (this method and 281 * {@link RepositorySystemSession#getUpdatePolicy()}) or also distinguish between artifact and 282 * metadata update policies (and use other methods), but <em>should not mix the two!</em> 283 * 284 * @param updatePolicy The global update policy, may be {@code null}/empty to apply the per-repository policies. 285 * @return This session for chaining, never {@code null}. 286 * @see RepositoryPolicy#UPDATE_POLICY_ALWAYS 287 * @see RepositoryPolicy#UPDATE_POLICY_DAILY 288 * @see RepositoryPolicy#UPDATE_POLICY_NEVER 289 * @see #setArtifactUpdatePolicy(String) 290 * @see #setMetadataUpdatePolicy(String) 291 */ 292 public DefaultRepositorySystemSession setUpdatePolicy(String updatePolicy) { 293 verifyStateForMutation(); 294 setArtifactUpdatePolicy(updatePolicy); 295 setMetadataUpdatePolicy(updatePolicy); 296 return this; 297 } 298 299 @Override 300 public String getArtifactUpdatePolicy() { 301 return artifactUpdatePolicy; 302 } 303 304 /** 305 * Sets the global artifact update policy. If set, the global update policy overrides the artifact update policies 306 * of the remote repositories being used for resolution. 307 * 308 * @param artifactUpdatePolicy The global update policy, may be {@code null}/empty to apply the per-repository policies. 309 * @return This session for chaining, never {@code null}. 310 * @see RepositoryPolicy#UPDATE_POLICY_ALWAYS 311 * @see RepositoryPolicy#UPDATE_POLICY_DAILY 312 * @see RepositoryPolicy#UPDATE_POLICY_NEVER 313 * @since TBD 314 */ 315 public DefaultRepositorySystemSession setArtifactUpdatePolicy(String artifactUpdatePolicy) { 316 verifyStateForMutation(); 317 this.artifactUpdatePolicy = artifactUpdatePolicy; 318 return this; 319 } 320 321 @Override 322 public String getMetadataUpdatePolicy() { 323 return metadataUpdatePolicy; 324 } 325 326 /** 327 * Sets the global metadata update policy. If set, the global update policy overrides the metadata update policies 328 * of the remote repositories being used for resolution. 329 * 330 * @param metadataUpdatePolicy The global update policy, may be {@code null}/empty to apply the per-repository policies. 331 * @return This session for chaining, never {@code null}. 332 * @see RepositoryPolicy#UPDATE_POLICY_ALWAYS 333 * @see RepositoryPolicy#UPDATE_POLICY_DAILY 334 * @see RepositoryPolicy#UPDATE_POLICY_NEVER 335 * @since TBD 336 */ 337 public DefaultRepositorySystemSession setMetadataUpdatePolicy(String metadataUpdatePolicy) { 338 verifyStateForMutation(); 339 this.metadataUpdatePolicy = metadataUpdatePolicy; 340 return this; 341 } 342 343 @Override 344 public LocalRepository getLocalRepository() { 345 LocalRepositoryManager lrm = getLocalRepositoryManager(); 346 return (lrm != null) ? lrm.getRepository() : null; 347 } 348 349 public LocalRepositoryManager getLocalRepositoryManager() { 350 return localRepositoryManager; 351 } 352 353 /** 354 * Sets the local repository manager used during this session. <em>Note:</em> Eventually, a valid session must have 355 * a local repository manager set. 356 * 357 * @param localRepositoryManager The local repository manager used during this session, may be {@code null}. 358 * @return This session for chaining, never {@code null}. 359 */ 360 public DefaultRepositorySystemSession setLocalRepositoryManager(LocalRepositoryManager localRepositoryManager) { 361 verifyStateForMutation(); 362 this.localRepositoryManager = localRepositoryManager; 363 return this; 364 } 365 366 @Override 367 public WorkspaceReader getWorkspaceReader() { 368 return workspaceReader; 369 } 370 371 /** 372 * Sets the workspace reader used during this session. If set, the workspace reader will usually be consulted first 373 * to resolve artifacts. 374 * 375 * @param workspaceReader The workspace reader for this session, may be {@code null} if none. 376 * @return This session for chaining, never {@code null}. 377 */ 378 public DefaultRepositorySystemSession setWorkspaceReader(WorkspaceReader workspaceReader) { 379 verifyStateForMutation(); 380 this.workspaceReader = workspaceReader; 381 return this; 382 } 383 384 @Override 385 public RepositoryListener getRepositoryListener() { 386 return repositoryListener; 387 } 388 389 /** 390 * Sets the listener being notified of actions in the repository system. 391 * 392 * @param repositoryListener The repository listener, may be {@code null} if none. 393 * @return This session for chaining, never {@code null}. 394 */ 395 public DefaultRepositorySystemSession setRepositoryListener(RepositoryListener repositoryListener) { 396 verifyStateForMutation(); 397 this.repositoryListener = repositoryListener; 398 return this; 399 } 400 401 @Override 402 public TransferListener getTransferListener() { 403 return transferListener; 404 } 405 406 /** 407 * Sets the listener being notified of uploads/downloads by the repository system. 408 * 409 * @param transferListener The transfer listener, may be {@code null} if none. 410 * @return This session for chaining, never {@code null}. 411 */ 412 public DefaultRepositorySystemSession setTransferListener(TransferListener transferListener) { 413 verifyStateForMutation(); 414 this.transferListener = transferListener; 415 return this; 416 } 417 418 @SuppressWarnings("checkstyle:magicnumber") 419 private <T> Map<String, T> copySafe(Map<?, ?> table, Class<T> valueType) { 420 Map<String, T> map; 421 if (table == null || table.isEmpty()) { 422 map = new HashMap<>(); 423 } else { 424 map = new HashMap<>((int) (table.size() / 0.75f) + 1); 425 for (Map.Entry<?, ?> entry : table.entrySet()) { 426 Object key = entry.getKey(); 427 if (key instanceof String) { 428 Object value = entry.getValue(); 429 if (valueType.isInstance(value)) { 430 map.put(key.toString(), valueType.cast(value)); 431 } 432 } 433 } 434 } 435 return map; 436 } 437 438 @Override 439 public Map<String, String> getSystemProperties() { 440 return systemPropertiesView; 441 } 442 443 /** 444 * Sets the system properties to use, e.g. for processing of artifact descriptors. System properties are usually 445 * collected from the runtime environment like {@link System#getProperties()} and environment variables. 446 * <p> 447 * <em>Note:</em> System properties are of type {@code Map<String, String>} and any key-value pair in the input map 448 * that doesn't match this type will be silently ignored. 449 * 450 * @param systemProperties The system properties, may be {@code null} or empty if none. 451 * @return This session for chaining, never {@code null}. 452 */ 453 public DefaultRepositorySystemSession setSystemProperties(Map<?, ?> systemProperties) { 454 verifyStateForMutation(); 455 this.systemProperties = copySafe(systemProperties, String.class); 456 systemPropertiesView = Collections.unmodifiableMap(this.systemProperties); 457 return this; 458 } 459 460 /** 461 * Sets the specified system property. 462 * 463 * @param key The property key, must not be {@code null}. 464 * @param value The property value, may be {@code null} to remove/unset the property. 465 * @return This session for chaining, never {@code null}. 466 */ 467 public DefaultRepositorySystemSession setSystemProperty(String key, String value) { 468 verifyStateForMutation(); 469 if (value != null) { 470 systemProperties.put(key, value); 471 } else { 472 systemProperties.remove(key); 473 } 474 return this; 475 } 476 477 @Override 478 public Map<String, String> getUserProperties() { 479 return userPropertiesView; 480 } 481 482 /** 483 * Sets the user properties to use, e.g. for processing of artifact descriptors. User properties are similar to 484 * system properties but are set on the discretion of the user and hence are considered of higher priority than 485 * system properties in case of conflicts. 486 * <p> 487 * <em>Note:</em> User properties are of type {@code Map<String, String>} and any key-value pair in the input map 488 * that doesn't match this type will be silently ignored. 489 * 490 * @param userProperties The user properties, may be {@code null} or empty if none. 491 * @return This session for chaining, never {@code null}. 492 */ 493 public DefaultRepositorySystemSession setUserProperties(Map<?, ?> userProperties) { 494 verifyStateForMutation(); 495 this.userProperties = copySafe(userProperties, String.class); 496 userPropertiesView = Collections.unmodifiableMap(this.userProperties); 497 return this; 498 } 499 500 /** 501 * Sets the specified user property. 502 * 503 * @param key The property key, must not be {@code null}. 504 * @param value The property value, may be {@code null} to remove/unset the property. 505 * @return This session for chaining, never {@code null}. 506 */ 507 public DefaultRepositorySystemSession setUserProperty(String key, String value) { 508 verifyStateForMutation(); 509 if (value != null) { 510 userProperties.put(key, value); 511 } else { 512 userProperties.remove(key); 513 } 514 return this; 515 } 516 517 @Override 518 public Map<String, Object> getConfigProperties() { 519 return configPropertiesView; 520 } 521 522 /** 523 * Sets the configuration properties used to tweak internal aspects of the repository system (e.g. thread pooling, 524 * connector-specific behavior, etc.). 525 * <p> 526 * <em>Note:</em> Configuration properties are of type {@code Map<String, Object>} and any key-value pair in the 527 * input map that doesn't match this type will be silently ignored. 528 * 529 * @param configProperties The configuration properties, may be {@code null} or empty if none. 530 * @return This session for chaining, never {@code null}. 531 */ 532 public DefaultRepositorySystemSession setConfigProperties(Map<?, ?> configProperties) { 533 verifyStateForMutation(); 534 this.configProperties = copySafe(configProperties, Object.class); 535 configPropertiesView = Collections.unmodifiableMap(this.configProperties); 536 return this; 537 } 538 539 /** 540 * Sets the specified configuration property. 541 * 542 * @param key The property key, must not be {@code null}. 543 * @param value The property value, may be {@code null} to remove/unset the property. 544 * @return This session for chaining, never {@code null}. 545 */ 546 public DefaultRepositorySystemSession setConfigProperty(String key, Object value) { 547 verifyStateForMutation(); 548 if (value != null) { 549 configProperties.put(key, value); 550 } else { 551 configProperties.remove(key); 552 } 553 return this; 554 } 555 556 @Override 557 public MirrorSelector getMirrorSelector() { 558 return mirrorSelector; 559 } 560 561 /** 562 * Sets the mirror selector to use for repositories discovered in artifact descriptors. Note that this selector is 563 * not used for remote repositories which are passed as request parameters to the repository system, those 564 * repositories are supposed to denote the effective repositories. 565 * 566 * @param mirrorSelector The mirror selector to use, may be {@code null}. 567 * @return This session for chaining, never {@code null}. 568 */ 569 public DefaultRepositorySystemSession setMirrorSelector(MirrorSelector mirrorSelector) { 570 verifyStateForMutation(); 571 this.mirrorSelector = mirrorSelector; 572 if (this.mirrorSelector == null) { 573 this.mirrorSelector = NullMirrorSelector.INSTANCE; 574 } 575 return this; 576 } 577 578 @Override 579 public ProxySelector getProxySelector() { 580 return proxySelector; 581 } 582 583 /** 584 * Sets the proxy selector to use for repositories discovered in artifact descriptors. Note that this selector is 585 * not used for remote repositories which are passed as request parameters to the repository system, those 586 * repositories are supposed to have their proxy (if any) already set. 587 * 588 * @param proxySelector The proxy selector to use, may be {@code null}. 589 * @return This session for chaining, never {@code null}. 590 * @see org.eclipse.aether.repository.RemoteRepository#getProxy() 591 */ 592 public DefaultRepositorySystemSession setProxySelector(ProxySelector proxySelector) { 593 verifyStateForMutation(); 594 this.proxySelector = proxySelector; 595 if (this.proxySelector == null) { 596 this.proxySelector = NullProxySelector.INSTANCE; 597 } 598 return this; 599 } 600 601 @Override 602 public AuthenticationSelector getAuthenticationSelector() { 603 return authenticationSelector; 604 } 605 606 /** 607 * Sets the authentication selector to use for repositories discovered in artifact descriptors. Note that this 608 * selector is not used for remote repositories which are passed as request parameters to the repository system, 609 * those repositories are supposed to have their authentication (if any) already set. 610 * 611 * @param authenticationSelector The authentication selector to use, may be {@code null}. 612 * @return This session for chaining, never {@code null}. 613 * @see org.eclipse.aether.repository.RemoteRepository#getAuthentication() 614 */ 615 public DefaultRepositorySystemSession setAuthenticationSelector(AuthenticationSelector authenticationSelector) { 616 verifyStateForMutation(); 617 this.authenticationSelector = authenticationSelector; 618 if (this.authenticationSelector == null) { 619 this.authenticationSelector = NullAuthenticationSelector.INSTANCE; 620 } 621 return this; 622 } 623 624 @Override 625 public ArtifactTypeRegistry getArtifactTypeRegistry() { 626 return artifactTypeRegistry; 627 } 628 629 /** 630 * Sets the registry of artifact types recognized by this session. 631 * 632 * @param artifactTypeRegistry The artifact type registry, may be {@code null}. 633 * @return This session for chaining, never {@code null}. 634 */ 635 public DefaultRepositorySystemSession setArtifactTypeRegistry(ArtifactTypeRegistry artifactTypeRegistry) { 636 verifyStateForMutation(); 637 this.artifactTypeRegistry = artifactTypeRegistry; 638 if (this.artifactTypeRegistry == null) { 639 this.artifactTypeRegistry = NullArtifactTypeRegistry.INSTANCE; 640 } 641 return this; 642 } 643 644 @Override 645 public DependencyTraverser getDependencyTraverser() { 646 return dependencyTraverser; 647 } 648 649 /** 650 * Sets the dependency traverser to use for building dependency graphs. 651 * 652 * @param dependencyTraverser The dependency traverser to use for building dependency graphs, may be {@code null}. 653 * @return This session for chaining, never {@code null}. 654 */ 655 public DefaultRepositorySystemSession setDependencyTraverser(DependencyTraverser dependencyTraverser) { 656 verifyStateForMutation(); 657 this.dependencyTraverser = dependencyTraverser; 658 return this; 659 } 660 661 @Override 662 public DependencyManager getDependencyManager() { 663 return dependencyManager; 664 } 665 666 /** 667 * Sets the dependency manager to use for building dependency graphs. 668 * 669 * @param dependencyManager The dependency manager to use for building dependency graphs, may be {@code null}. 670 * @return This session for chaining, never {@code null}. 671 */ 672 public DefaultRepositorySystemSession setDependencyManager(DependencyManager dependencyManager) { 673 verifyStateForMutation(); 674 this.dependencyManager = dependencyManager; 675 return this; 676 } 677 678 @Override 679 public DependencySelector getDependencySelector() { 680 return dependencySelector; 681 } 682 683 /** 684 * Sets the dependency selector to use for building dependency graphs. 685 * 686 * @param dependencySelector The dependency selector to use for building dependency graphs, may be {@code null}. 687 * @return This session for chaining, never {@code null}. 688 */ 689 public DefaultRepositorySystemSession setDependencySelector(DependencySelector dependencySelector) { 690 verifyStateForMutation(); 691 this.dependencySelector = dependencySelector; 692 return this; 693 } 694 695 @Override 696 public VersionFilter getVersionFilter() { 697 return versionFilter; 698 } 699 700 /** 701 * Sets the version filter to use for building dependency graphs. 702 * 703 * @param versionFilter The version filter to use for building dependency graphs, may be {@code null} to not filter 704 * versions. 705 * @return This session for chaining, never {@code null}. 706 */ 707 public DefaultRepositorySystemSession setVersionFilter(VersionFilter versionFilter) { 708 verifyStateForMutation(); 709 this.versionFilter = versionFilter; 710 return this; 711 } 712 713 @Override 714 public DependencyGraphTransformer getDependencyGraphTransformer() { 715 return dependencyGraphTransformer; 716 } 717 718 /** 719 * Sets the dependency graph transformer to use for building dependency graphs. 720 * 721 * @param dependencyGraphTransformer The dependency graph transformer to use for building dependency graphs, may be 722 * {@code null}. 723 * @return This session for chaining, never {@code null}. 724 */ 725 public DefaultRepositorySystemSession setDependencyGraphTransformer( 726 DependencyGraphTransformer dependencyGraphTransformer) { 727 verifyStateForMutation(); 728 this.dependencyGraphTransformer = dependencyGraphTransformer; 729 return this; 730 } 731 732 @Override 733 public SessionData getData() { 734 return data; 735 } 736 737 /** 738 * Sets the custom data associated with this session. 739 * 740 * @param data The session data, may be {@code null}. 741 * @return This session for chaining, never {@code null}. 742 */ 743 public DefaultRepositorySystemSession setData(SessionData data) { 744 verifyStateForMutation(); 745 this.data = data; 746 if (this.data == null) { 747 this.data = new DefaultSessionData(); 748 } 749 return this; 750 } 751 752 @Override 753 public RepositoryCache getCache() { 754 return cache; 755 } 756 757 /** 758 * Sets the cache the repository system may use to save data for future reuse during the session. 759 * 760 * @param cache The repository cache, may be {@code null} if none. 761 * @return This session for chaining, never {@code null}. 762 */ 763 public DefaultRepositorySystemSession setCache(RepositoryCache cache) { 764 verifyStateForMutation(); 765 this.cache = cache; 766 return this; 767 } 768 769 /** 770 * Marks this session as read-only such that any future attempts to call its mutators will fail with an exception. 771 * Marking an already read-only session as read-only has no effect. The session's data and cache remain writable 772 * though. 773 */ 774 public void setReadOnly() { 775 readOnly = true; 776 } 777 778 /** 779 * Verifies this instance state for mutation operations: mutated instance must not be read-only or closed. 780 */ 781 private void verifyStateForMutation() { 782 if (readOnly) { 783 throw new IllegalStateException("repository system session is read-only"); 784 } 785 } 786 787 static class NullProxySelector implements ProxySelector { 788 789 public static final ProxySelector INSTANCE = new NullProxySelector(); 790 791 public Proxy getProxy(RemoteRepository repository) { 792 requireNonNull(repository, "repository cannot be null"); 793 return repository.getProxy(); 794 } 795 } 796 797 static class NullMirrorSelector implements MirrorSelector { 798 799 public static final MirrorSelector INSTANCE = new NullMirrorSelector(); 800 801 public RemoteRepository getMirror(RemoteRepository repository) { 802 requireNonNull(repository, "repository cannot be null"); 803 return null; 804 } 805 } 806 807 static class NullAuthenticationSelector implements AuthenticationSelector { 808 809 public static final AuthenticationSelector INSTANCE = new NullAuthenticationSelector(); 810 811 public Authentication getAuthentication(RemoteRepository repository) { 812 requireNonNull(repository, "repository cannot be null"); 813 return repository.getAuthentication(); 814 } 815 } 816 817 static final class NullArtifactTypeRegistry implements ArtifactTypeRegistry { 818 819 public static final ArtifactTypeRegistry INSTANCE = new NullArtifactTypeRegistry(); 820 821 public ArtifactType get(String typeId) { 822 return null; 823 } 824 } 825}