How should a service which needs to be stoppable, but not by clients, be stopped?
The easy answer is to have an interface with all the regular operations which also includes a stop() method.
interface Service {
operation( parameters ...);
somethingElse( parameters ... );
stop();
}
The main problem with the开发者_Python百科 stop method is that most clients who get a reference to a Service should probably not also be able to stop the service.
Another alternative is to simply define two interfaces, the service and the Stoppable
interface Service {
operation( parameters ...);
somethingElse( parameters ... );
}
interface Stoppable {
void stop();
}
The only problem with this approach is if the implementation is wrapped by another Service, then the stop method is hidden away.
The original problem of stopping clients from "stopping" your service is still possible, they just need to first check if the reference is an instance of Stoppable and then they can "stop" it.
How would you solve this problem?
I have an idea which solves the problem elegantly (well for me) without leaving a public stop available. However before I show it, I'd like some ideas.
Use interface inheritance:
interface Service {
operation( parameters ...);
somethingElse( parameters ... );
}
interface StoppableService extends Service {
void stop();
}
Clients that only need the raw Service get given that by an appropriate factory method. Anything that should be able to stop the service, request the StoppableService.
If you are worried about clients casting to StoppableService can calling stop(), then you'll need your concrete implementations to separate out this function. Give them a concrete implementation that has a no-op version of stop(). You can still have your factory provide a working implementation of stop() to anyone who should be able stop it. Perhaps when they ask for an implementation from your factory, they can pass in appropriate credentials so you can determine what they should be able to do and give them the correct version.
You could do something like
interface Service {
operation( parameters ...);
somethingElse( parameters ... );
<E> E getControlInterface(Class<E> clazz);
}
and then
Stoppable stoppable = service.getControlInterface(Stoppable.class);
if (stoppable != null) {
stoppable.stop();
}
But I think this is overcomplicating, implementing Stoppable
interface should be enough. The wrappers should be aware of Stoppable
and implement it also.
精彩评论