* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
- */
+ */
package org.wamblee.system.core;
import java.util.ArrayList;
/**
* Abstract subsystem class making it easy to implement new subsystems.
*/
-public abstract class AbstractComponent implements Component {
+public abstract class AbstractComponent<Type> implements Component<Type> {
private static final Log LOG = LogFactory.getLog(AbstractComponent.class);
- private Status _status;
- private String _context;
- private String _name;
+ private ThreadLocal<List<ProvidedInterface>> _remaining;
+
+ private String _context;
+ private String _name;
private List<ProvidedInterface> _provided;
private List<RequiredInterface> _required;
- private Set<ProvidedInterface> _running;
-
+
/**
* Constructs the subsystem.
- *
+ *
* @param aName
* Name of the system.
* @param aProvided
*/
protected AbstractComponent(String aName, ProvidedInterface[] aProvided,
RequiredInterface[] aRequired) {
- _status = Status.NOT_STARTED;
- _context = null;
+ _remaining = new ThreadLocal<List<ProvidedInterface>>();
+ _context = null;
_name = aName;
_provided = new ArrayList<ProvidedInterface>();
_provided.addAll(Arrays.asList(aProvided));
_required = new ArrayList<RequiredInterface>();
_required.addAll(Arrays.asList(aRequired));
- _running = new HashSet<ProvidedInterface>();
}
- @Override
- public Status getStatus() {
- return _status;
+ protected AbstractComponent(String aName) {
+ this(aName, new ProvidedInterface[0], new RequiredInterface[0]);
}
-
+
+ public AbstractComponent addProvidedInterface(ProvidedInterface aProvided) {
+ _provided.add(aProvided);
+ return this;
+ }
+
+ public AbstractComponent addRequiredInterface(RequiredInterface aRequired) {
+ _required.add(aRequired);
+ return this;
+ }
+
@Override
public final String getName() {
return _name;
}
-
+
@Override
public void addContext(String aContext) {
- if (_context == null ) {
- _context = aContext;
- }
- else {
+ if (_context == null) {
+ _context = aContext;
+ } else {
_context = aContext + "." + _context;
}
}
+ @Override
+ public String getContext() {
+ return _context;
+ }
+
@Override
public String getQualifiedName() {
- if ( _context == null ) {
- return getName();
+ if (_context == null) {
+ return getName();
}
- return _context + "." + getName();
+ return _context + "." + getName();
}
@Override
}
@Override
- public final void start() {
+ public final Type start(Scope aScope) {
LOG.info("Initializing '" + getQualifiedName() + "'");
- doStart();
- _status = Status.RUNNING;
- if ( _running.size() != _provided.size()) {
- List<ProvidedInterface> remaining =
- new ArrayList<ProvidedInterface>(_provided);
- remaining.removeAll(_running);
- throw new SystemAssemblyException(getQualifiedName() + ": not all services were started, missing " + remaining);
+ List<ProvidedInterface> oldRemaining = _remaining.get();
+ _remaining.set(new ArrayList<ProvidedInterface>(Arrays.asList(getProvidedInterfaces())));
+ try {
+ Type runtime = doStart(aScope);
+ checkNotStartedInterfaces();
+ return runtime;
+ } finally {
+ _remaining.set(oldRemaining);
+ }
+ }
+
+ private void checkNotStartedInterfaces() {
+ if (_remaining.get().size() > 0) {
+ String notProvided = "";
+ for (ProvidedInterface provided : _remaining.get()) {
+ notProvided += "\nComponent " + getQualifiedName()
+ + " did not start interface " + provided;
+ }
+ throw new SystemAssemblyException(notProvided);
}
}
/**
* Must be implemented for initializing the subsystem. The implementation
* must call {@link #addService(Service)} for each service that is started.
+ *
+ * @return Returns the runtime of the component.
*/
- protected abstract void doStart();
+ protected abstract Type doStart(Scope aScope);
/**
* Implementations must call this method to indicate that a new service has
* been started.
*
+ * @param aDescriptor
+ * Provided interface.
* @param aService
- * Service.
+ * Implementation of the interface.
+ * @param aScope
+ * scope in which to publish the implementation.
*/
- protected final void addService(
- ProvidedInterface aDescriptor, Object aService) {
- LOG.info("Interface '" + getQualifiedName() + "." + aDescriptor.getName() + "' started.");
- _running.add(aDescriptor);
- aDescriptor.publish(aService);
+ protected final void addInterface(ProvidedInterface aDescriptor,
+ Object aService, Scope aScope) {
+ LOG.info("Interface '" + getQualifiedName() + "."
+ + aDescriptor.getName() + "' started.");
+ _remaining.get().remove(aDescriptor);
+ aScope.publishInterface(aDescriptor, aService);
}
@Override
- public ProvidedInterface[] getRunningServices() {
- return _running.toArray(new ProvidedInterface[0]);
- }
-
- @Override
- public void stop() {
- doStop();
- _status = Status.STOPPED;
+ public void stop(Type aRuntime) {
+ LOG.info("Stopping '" + getQualifiedName() + "'");
+ doStop(aRuntime);
}
-
- protected abstract void doStop();
+
+ protected abstract void doStop(Type aRuntime);
@Override
public String toString() {
- return _name;
+ return getQualifiedName();
}
}