Uses the {@link ServiceLoader} to load all SPI implementations of the
passed class

@param <T>
The implementation type to be loaded
@param aSPIClass
The SPI interface class. May not be <code>null</code>.
@return A list of all currently available plugins
779317
@Nonnull
  @ReturnsMutableCopy
  public static <T> ICommonsList <T> getAllSPIImplementations (@Nonnull final Class <T> aSPIClass)
  {
    return getAllSPIImplementations (aSPIClass, ClassLoaderHelper.getDefaultClassLoader (), null);
  }
277699
private static ClassLoader[] getClassLoaders(ClassLoader classLoader) {
		return new ClassLoader[] { classLoader, Thread.currentThread().getContextClassLoader(), ClassLoaderUtils.class.getClassLoader(),
				systemClassLoader };
	}
708338
public static <T> List<T> load(final Class<T> type, final ClassLoader classLoader) {
        final List<T> loaded = new ArrayList<>();
        final Iterator<T> iterator = ServiceLoader.load(type, classLoader).iterator();
        while (hasNextSafely(iterator)) {
            try {
                final T next = iterator.next();
                loaded.add(next);
                LOGGER.debug("Found {}", type);
            } catch (Exception e) {
                LOGGER.error("Could not load {}: {}", type, e);
            }
        }
        return loaded;
    }
109881
private List<AddOnModel> loadAddOns() {
        debug("searching for addons in: " + getMain().getFileSystemManager().getLibLocation());
        PluginManager pluginManager = new DefaultPluginManager(getMain().getFileSystemManager().getLibLocation(),
                new ArrayList<>(aspectOrAffectedSet));
        // load the plugins
        debug("loading plugins");
        pluginManager.loadPlugins();
        debug("loaded: " + pluginManager.getPlugins().toString());

        // start (active/resolved) the plugins
        try {
            debug("starting plugins");
            pluginManager.startPlugins();
        } catch (Exception | NoClassDefFoundError e) {
            error("Error while trying to start the PF4J-Plugins", e);
        }
        try {
            debug("retrieving addons from the plugins");
            List<AddOnModel> addOns = pluginManager.getExtensions(AddOnModel.class);
            debug("retrieved: " + addOns.toString());
            KeyManager keyManager = new KeyManager();
            addOns.stream()
                    .filter(addOn -> addOn.getClass().getClassLoader() instanceof IzouPluginClassLoader)
                    .forEach(addOn -> {
                        IzouPluginClassLoader izouPluginClassLoader = (IzouPluginClassLoader) addOn.getClass()
                                .getClassLoader();
                        PluginWrapper plugin = pluginManager.getPlugin(izouPluginClassLoader.getPluginDescriptor()
                                .getPluginId());
                        keyManager.manageAddOnKey(plugin.getDescriptor());
                        pluginWrappers.put(addOn, plugin);
                        addOn.setPlugin(plugin);
                    });
            keyManager.saveAddOnKeys();
            return addOns;
        } catch (Exception e) {
            log.fatal("Error while trying to start the AddOns", e);
            return new ArrayList<>();
        }
    }
211083
@Override
    public T addAsServiceProviderAndClasses(Class<?> serviceInterface, Class<?>... serviceImpls)
        throws IllegalArgumentException {
        Validate.notNull(serviceInterface, "ServiceInterface must be specified");
        Validate.notNullAndNoNullValues(serviceImpls, "ServiceImpls must be specified and can not contain null values");

        addAsServiceProvider(serviceInterface, serviceImpls);
        addClass(serviceInterface);
        return addClasses(serviceImpls);
    }
396830
@Override
    public List<ServiceInfo> getServiceInfos(Class serviceClass) {
        final LinkedList<ServiceInfo> result = new LinkedList<ServiceInfo>();
        for (ServiceInfo serviceInfo : services.values()) {
            if (serviceInfo.isInstanceOf(serviceClass)) {
                if (serviceInfo.isCoreService()) {
                    result.addFirst(serviceInfo);
                } else {
                    result.addLast(serviceInfo);
                }
            }
        }
        return result;
    }
171766
@Override
  public Class<?> loadClassImpl(String name, boolean resolve)
    throws ClassNotFoundException
  {
    // The JVM has already cached the classes, so we don't need to
    Class<?> cl = findLoadedClass(name);

    if (cl != null) {
      if (resolve)
        resolveClass(cl);
      return cl;
    }
    // System.out.println("ROOT: " + name);
    if (_classNotFoundCache.get(name) != null) {
      return null;
    }
    
    try {
      cl = super.loadClassImpl(name, resolve);
    } catch (ClassNotFoundException e) {
      _classNotFoundCache.put(name, name);
      
      throw e;
    }
    
    if (cl == null) {
      _classNotFoundCache.put(name, name);
    }
    
    return cl;
  }
461351
private List<I_CmsWorkplaceAppConfiguration> loadAppsUsingServiceLoader() {

        List<I_CmsWorkplaceAppConfiguration> appConfigurations = new ArrayList<I_CmsWorkplaceAppConfiguration>();
        Iterator<I_CmsWorkplaceAppConfiguration> configs = ServiceLoader.load(
            I_CmsWorkplaceAppConfiguration.class).iterator();
        while (configs.hasNext()) {
            try {
                I_CmsWorkplaceAppConfiguration config = configs.next();
                appConfigurations.add(config);
            } catch (Throwable t) {
                LOG.error("Error loading workplace app configuration from classpath.", t);
            }
        }
        return appConfigurations;
    }
928253
public <T extends ServiceConfiguration<?>> List<T> getExistingServiceConfigurations(Class<T> clazz) {
    ArrayList<T> results = new ArrayList<>();
    for (ServiceConfiguration<?> serviceConfiguration : serviceConfigurations) {
      if (clazz.equals(serviceConfiguration.getClass())) {
        results.add(clazz.cast(serviceConfiguration));
      }
    }
    return results;
  }
71336
public static <S> S loadOptionalService(Class<S> serviceInterface)
  {
    S service = null;
    ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
    if(classLoader != null) {
      service = loadService(serviceInterface, classLoader);
    }
    if(service == null) {
      service = loadService(serviceInterface, Classes.class.getClassLoader());
    }
    return service;
  }
527932
@SuppressWarnings("unchecked")
	public static <T> List<T> getInstanceList(Class<T> type) {
		if (type == null) {
			throw new IllegalArgumentException("Type should not be empty");
		}

		List<T> loader = (List<T>) EXTENSION_LOCATOR.get(type);
		if (loader == null) {
			try {
				lock.lock();
				List<T> instanceList = new ArrayList<T>();
				ServiceLoader<T> serviceLoader = ServiceLoader.load(type);
				for (T service : serviceLoader) {
					instanceList.add(service);
				}
				loader = instanceList;
				if (EXTENSION_LOCATOR.putIfAbsent(type, instanceList) != instanceList) {
					loader = (List<T>) EXTENSION_LOCATOR.get(type);
				}
			} catch (Exception e) {
				LOG.error("Error to load SPI instances from META-INF/services/" + type, e);
			} finally {
				lock.unlock();
			}
		}
		return loader;
	}
1148416
public <S> ServiceBinder<S> bindServices(final Class<S> type) {
        ServiceBinderImpl<S> binder = new ServiceBinderImpl<S>(type);
        binders.add(binder);
        return binder;
    }
1270343
private <T> Set<Class<? extends T>> load(Class<T> serviceClass) {
        String serviceFile = SERVICES + "/" + serviceClass.getName();

        LinkedHashSet<Class<? extends T>> providers = new LinkedHashSet<Class<? extends T>>();

        try {
            Enumeration<URL> enumeration = classLoader.getResources(serviceFile);
            while (enumeration.hasMoreElements()) {
                final URL url = enumeration.nextElement();
                final InputStream is = url.openStream();
                BufferedReader reader = null;

                try {
                    reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
                    String line = reader.readLine();
                    while (null != line) {
                        line = skipCommentAndTrim(line);

                        if (line.length() > 0) {
                            try {
                                Class<? extends T> provider = classLoader.loadClass(line).asSubclass(serviceClass);
                                providers.add(provider);
                            } catch (ClassCastException e) {
                                ClassLoader other = serviceClass.getClassLoader();
                                if (!classLoader.getClass().equals(serviceClass.getClassLoader())) {
                                    throw new IllegalStateException("Service " + line
                                        + " was loaded by different classloader (" + (other == null ? "bootstrap"
                                            : other.getClass().getName()) + ") then service interface "
                                        + serviceClass.getName() + " (" + classLoader.getClass().getName()
                                        + "), unable to cast classes");
                                }
                                throw new IllegalStateException("Service " + line + " does not implement expected type "
                                    + serviceClass.getName());
                            }
                        }
                        line = reader.readLine();
                    }
                } finally {
                    if (reader != null) {
                        reader.close();
                    }
                }
            }
        } catch (Exception e) {
            throw new RuntimeException("Could not load services for " + serviceClass.getName(), e);
        }
        return providers;
    }
532890
private boolean loadFacesInitPluginsJDK6()
    {
        String[] pluginEntries = null;
        try
        {
            Class serviceLoader = ClassUtils.getContextClassLoader().loadClass("java.util.ServiceLoader");
            Method m = serviceLoader.getDeclaredMethod("load", Class.class, ClassLoader.class);
            Object loader = m.invoke(serviceLoader, StartupListener.class, ClassUtils.getContextClassLoader());
            m = loader.getClass().getDeclaredMethod("iterator");
            Iterator<StartupListener> it = (Iterator<StartupListener>) m.invoke(loader);
            List<StartupListener> listeners = new LinkedList<StartupListener>();
            if (!it.hasNext())
            {
                return false;
            }
            while (it.hasNext())
            {
                listeners.add(it.next());
            }
            //StartupListener[] listeners1 = listeners.toArray(new StartupListener[listeners.size()]);
            _servletContext.setAttribute(FACES_INIT_PLUGINS, listeners);
            return true;
        }
        catch (ClassNotFoundException e)
        {

        }
        catch (NoSuchMethodException e)
        {
            log.log(Level.SEVERE, e.getMessage(), e);
        }
        catch (InvocationTargetException e)
        {
            log.log(Level.SEVERE, e.getMessage(), e);
        }
        catch (IllegalAccessException e)
        {
            log.log(Level.SEVERE, e.getMessage(), e);
        }
        return false;
    }
839220
public static <E> Collection<E> get(Class<? extends E> service) {

        Iterator<? extends E> implementations = ServiceLoader.load(service).iterator();

        Collection<E> result = new ArrayList<E>();
        while (implementations.hasNext()) {
            result.add(implementations.next());
        }
        return result;

    }
863337
public static <T> Collection<T> loadEnriched(final Class<T> serviceClass)
   {
      try
      {
         Collection<T> services = new ArrayList<T>();
         ServiceEnricher origin = null;

         if (!NonEnriching.class.isAssignableFrom(serviceClass))
         {
            if (enricherLoader == null)
            {
               enricherLoader = java.util.ServiceLoader
                        .load(ServiceEnricher.class);
            }

            for (ServiceEnricher enricher : enricherLoader)
            {
               services = enricher.produce(serviceClass);
               if (services == null)
               {
                  services = new ArrayList<T>();
               }
               if (!services.isEmpty())
               {
                  origin = enricher;
                  break;
               }
            }
         }

         if (services.isEmpty())
         {
            Constructor<? extends T> constructor = serviceClass.getDeclaredConstructor();
            constructor.setAccessible(true);
            services.add(constructor.newInstance());
         }

         if (!NonEnriching.class.isAssignableFrom(serviceClass))
         {
            for (ServiceEnricher enricher : enricherLoader)
            {
               if (!enricher.equals(origin))
               {
                  for (T service : services) {
                     enricher.enrich(service);
                  }
               }
            }
         }

         return services;
      }
      catch (NoClassDefFoundError e)
      {
         throw new RuntimeException("Could not instantiate service class " + serviceClass.getName(), e);
      }
      catch (InvocationTargetException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e.getCause());
      }
      catch (IllegalArgumentException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e);
      }
      catch (InstantiationException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e);
      }
      catch (IllegalAccessException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e);
      }
      catch (SecurityException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e);
      }
      catch (NoSuchMethodException e)
      {
         throw new RuntimeException("Error instantiating " + serviceClass, e);
      }
   }
824978
private ClassLoader loadJobTypeClassLoader(final File pluginDir,
      final String jobTypeName, final JobTypePluginSet plugins) {
    // sysconf says what jars/confs to load
    final List<URL> resources = new ArrayList<>();
    final Props pluginLoadProps = plugins.getPluginLoaderProps(jobTypeName);

    try {
      // first global classpath
      logger.info("Adding global resources for " + jobTypeName);
      final List<String> typeGlobalClassPath =
          pluginLoadProps.getStringList("jobtype.global.classpath", null, ",");
      if (typeGlobalClassPath != null) {
        for (final String jar : typeGlobalClassPath) {
          final URL cpItem = new File(jar).toURI().toURL();
          if (!resources.contains(cpItem)) {
            logger.info("adding to classpath " + cpItem);
            resources.add(cpItem);
          }
        }
      }

      // type specific classpath
      logger.info("Adding type resources.");
      final List<String> typeClassPath =
          pluginLoadProps.getStringList("jobtype.classpath", null, ",");
      if (typeClassPath != null) {
        for (final String jar : typeClassPath) {
          final URL cpItem = new File(jar).toURI().toURL();
          if (!resources.contains(cpItem)) {
            logger.info("adding to classpath " + cpItem);
            resources.add(cpItem);
          }
        }
      }
      final List<String> jobtypeLibDirs =
          pluginLoadProps.getStringList("jobtype.lib.dir", null, ",");
      if (jobtypeLibDirs != null) {
        for (final String libDir : jobtypeLibDirs) {
          for (final File f : new File(libDir).listFiles()) {
            if (f.getName().endsWith(".jar")) {
              resources.add(f.toURI().toURL());
              logger.info("adding to classpath " + f.toURI().toURL());
            }
          }
        }
      }

      logger.info("Adding type override resources.");
      for (final File f : pluginDir.listFiles()) {
        if (f.getName().endsWith(".jar")) {
          resources.add(f.toURI().toURL());
          logger.info("adding to classpath " + f.toURI().toURL());
        }
      }

    } catch (final MalformedURLException e) {
      throw new JobTypeManagerException(e);
    }

    // each job type can have a different class loader
    logger.info(String
        .format("Classpath for plugin[dir: %s, JobType: %s]: %s", pluginDir, jobTypeName,
            resources));
    final ClassLoader jobTypeLoader =
        new URLClassLoader(resources.toArray(new URL[resources.size()]),
            this.parentLoader);
    return jobTypeLoader;
  }