Understanding Java SPI, Dubbo SPI, and Spring SPI Mechanisms
This article explains the Service Provider Interface (SPI) concept, demonstrates how Java's built‑in SPI, Dubbo's enhanced SPI, and Spring's SPI work with code examples, compares their strengths and limitations, and discusses classpath ordering and extension loading issues.
SPI (Service Provider Interface) is a service discovery mechanism that allows an interface's implementation class names to be listed in configuration files and loaded at runtime, enabling dynamic replacement of implementations.
JDK SPI Example
Consider a simple logging framework super‑logger with a configuration interface and an XML implementation:
package com.github.kongwu.spisamples;
public interface SuperLoggerConfiguration {
void configure(String configFile);
} package com.github.kongwu.spisamples;
public class XMLConfiguration implements SuperLoggerConfiguration {
public void configure(String configFile) {
// ...
}
}The factory loads the implementation via ServiceLoader:
ServiceLoader<SuperLoggerConfiguration> serviceLoader = ServiceLoader.load(SuperLoggerConfiguration.class);
Iterator<SuperLoggerConfiguration> iterator = serviceLoader.iterator();
SuperLoggerConfiguration configuration;
while (iterator.hasNext()) {
configuration = iterator.next(); // load and init
}
configuration.configure(configFile);Using an iterator means the last discovered implementation is used, which depends on the classpath order and can lead to unpredictable results when multiple implementations exist.
Dubbo SPI
Dubbo enhances SPI with named extensions. Configuration files are placed under META-INF/dubbo and use key‑value pairs, allowing retrieval of a specific implementation by its alias.
optimusPrime = org.apache.spi.OptimusPrime
bumblebee = org.apache.spi.BumblebeeInterface definitions are annotated with @SPI, and extensions are loaded via ExtensionLoader:
@SPI
public interface Robot {
void sayHello();
}
public class OptimusPrime implements Robot {
@Override public void sayHello() { System.out.println("Hello, I am Optimus Prime."); }
}
public class Bumblebee implements Robot {
@Override public void sayHello() { System.out.println("Hello, I am Bumblebee."); }
}
ExtensionLoader<Robot> loader = ExtensionLoader.getExtensionLoader(Robot.class);
Robot optimus = loader.getExtension("optimusPrime");
optimus.sayHello();
Robot bumble = loader.getExtension("bumblebee");
bumble.sayHello();Dubbo also supports a default extension via the @SPI("defaultName") value and an adaptive mechanism.
Spring SPI
Spring uses a single file META-INF/spring.factories where each line maps an interface to one or more implementation classes. The framework loads all factories via SpringFactoriesLoader:
List<LoggingSystemFactory> factories = SpringFactoriesLoader.loadFactories(LoggingSystemFactory.class, classLoader);Example snippet from Spring Boot's spring.factories:
# Logging Systems
org.springframework.boot.logging.LoggingSystemFactory=\
org.springframework.boot.logging.logback.LogbackLoggingSystem.Factory,\
org.springframework.boot.logging.log4j2.Log4J2LoggingSystem.Factory,\
org.springframework.boot.logging.java.JavaLoggingSystem.FactorySpring’s SPI does not support aliases, so all discovered implementations are added to a list in classpath order.
Comparison
JDK SPI is the simplest but least flexible, relying solely on classpath order. Dubbo SPI offers the richest feature set—named extensions, default implementations, adaptive loading—but is tied to the Dubbo ecosystem. Spring SPI improves usability by consolidating extensions into a single file and integrates smoothly with Spring Boot, though its capabilities are comparable to JDK SPI.
Choosing the appropriate SPI mechanism depends on the project’s ecosystem and the need for extensibility control.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Top Architect
Top Architect focuses on sharing practical architecture knowledge, covering enterprise, system, website, large‑scale distributed, and high‑availability architectures, plus architecture adjustments using internet technologies. We welcome idea‑driven, sharing‑oriented architects to exchange and learn together.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
