public CachingRepositoryManager(
      AbstractRepositoryManager<T> delegate, int repositoryType, CachingTransport transport) {
    this.delegate = delegate;
    this.repositoryType = repositoryType;

    if (transport == null) {
      Object t = delegate.getAgent().getService(Transport.SERVICE_NAME);
      if (t instanceof CachingTransport) {
        transport = (CachingTransport) t;
      }
    }

    this.transport = transport;
  }
  public IRepository<T> loadRepository(
      URI location, IProgressMonitor monitor, String type, int flags) throws ProvisionException {
    checkValidLocation(location);
    SubMonitor sub = SubMonitor.convert(monitor, 100);
    boolean added = false;
    IRepository<T> result = null;

    try {
      CachingTransport.startLoadingRepository(location);
      enterLoad(location, sub.newChild(5));

      result = basicGetRepository(location);
      if (result != null) {
        return result;
      }

      // Add the repository first so that it will be enabled, but don't send add event until after
      // the load.
      added = addRepository(location, true, false);

      LocationProperties indexFile = loadIndexFile(location, sub.newChild(15));
      String[] preferredOrder = getPreferredRepositorySearchOrder(indexFile);
      String[] allSuffixes = getAllSuffixes();
      String[] suffixes = sortSuffixes(allSuffixes, preferredOrder);

      sub =
          SubMonitor.convert(
              sub, NLS.bind("Adding repository {0}", location), suffixes.length * 100);
      ProvisionException failure = null;

      try {
        for (int i = 0; i < suffixes.length; i++) {
          if (sub.isCanceled()) {
            throw new OperationCanceledException();
          }

          try {
            result = loadRepository(location, suffixes[i], type, flags, sub.newChild(100));
          } catch (ProvisionException e) {
            failure = e;
            break;
          }

          if (result != null) {
            addRepository(result, false, suffixes[i]);
            cacheIndexFile(location, suffixes[i]);
            break;
          }
        }
      } finally {
        sub.done();
      }

      if (result == null) {
        // If we just added the repository, remove it because it cannot be loaded.
        if (added) {
          removeRepository(location, false);
        }

        // Eagerly cleanup missing system repositories.
        if (Boolean.valueOf(delegate.getRepositoryProperty(location, IRepository.PROP_SYSTEM))
            .booleanValue()) {
          delegate.removeRepository(location);
        }

        if (failure != null) {
          throw failure;
        }

        fail(location, ProvisionException.REPOSITORY_NOT_FOUND);
      }
    } finally {
      CachingTransport.stopLoadingRepository();
      exitLoad(location);
    }

    // Broadcast the add event after releasing lock.
    if (added) {
      broadcastChangeEvent(location, repositoryType, RepositoryEvent.ADDED, true);
    }

    return result;
  }