I have a set of API classes which contain only static methods and a single private constructor so they cannot be instantiated. However, I would like a third party developer to be able to modify the behaviour of the API's to suit their needs.
This is the solution I have so far (dependency injection via static setter method). This is the public API class that the developer would use. As you can see, it has a dependency on StaticApiImpl
.
public class StaticApi {
private static StaticApiImpl impl = new StaticApiImpl();
private StaticApi() {}
public static void setImpl(StaticApiImpl impl) {
StaticApi.impl = impl;
}
public static void doThing() {
impl.doThing();
}
}
This is the default API implementation as coded myself.
public class StaticApiImpl {
public void doThing() {
System.out.println("Do thing the default way.");
}
}
This is a hypothetical extended version of the default implementation that a third party might write:
public class MyCustomStaticApiImpl extends StaticApiImpl {
@Override
public void doThing() {
System.out.println("Do thing differently.");
}
}
The developer would then simply inject their dependency via the setter method upon initialisation of their plugin:
public void onLoad() throws Exception {
StaticApi.setImpl(new MyCustomStaticApiImpl());
}
My question is: is this the correct way of doing it? Is there perhaps some design pattern dedicated to cases such as this that I have not heard of?
The best solution for your 3rd party developer will be using the Proxy
pattern.
http://en.wikipedia.org/wiki/Proxy_pattern
Setting the implementation object as instance is not great solution.
What you are setting up here is a factory pattern with the ability for clients to configure which implementation the factory returns. That is fine, but there are a couple of things that you need to do differently.
StaticApi
to StaticApiFactory
. This will make its role more clear and avoid a naming conflict with the next parts. public static void doSomething()
method. There's no need to redefine all of your API methods as static methods. Since that is a factory class, all you need instead is a method to get the current implementation, eg a public static StaticApi getInstance()
method that returns the implementation that has been set via setImpl()
. StaticApi
that defines the contract of the APIs behavior. The factory class should then allow the clients to setImpl(StaticApi)
. StaticApiFactory.getInstance()
.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.