001: /**
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */package org.apache.geronimo.gbean.runtime;
017:
018: import org.apache.geronimo.gbean.AbstractName;
019: import org.apache.geronimo.gbean.GReferenceInfo;
020: import org.apache.geronimo.gbean.InvalidConfigurationException;
021: import org.apache.geronimo.gbean.ReferencePatterns;
022: import org.apache.geronimo.gbean.AbstractNameQuery;
023: import org.apache.geronimo.kernel.Kernel;
024: import org.apache.geronimo.kernel.lifecycle.LifecycleAdapter;
025: import org.apache.geronimo.kernel.lifecycle.LifecycleListener;
026:
027: import java.util.Collections;
028: import java.util.HashSet;
029: import java.util.Iterator;
030: import java.util.Set;
031:
032: /**
033: * @version $Rev:386515 $ $Date: 2006-11-16 20:35:17 -0800 (Thu, 16 Nov 2006) $
034: */
035: public class GBeanCollectionReference extends AbstractGBeanReference {
036: /**
037: * is this reference online
038: */
039: private boolean isOnline = false;
040:
041: /**
042: * The target objectName patterns to watch for a connection.
043: */
044: private Set patterns = Collections.EMPTY_SET;
045:
046: /**
047: * Current set of targets
048: */
049: private final Set targets = new HashSet();
050:
051: /**
052: * Our listener for lifecycle events
053: */
054: private final LifecycleListener listener;
055:
056: public GBeanCollectionReference(GBeanInstance gbeanInstance,
057: GReferenceInfo referenceInfo, Kernel kernel,
058: ReferencePatterns referencePatterns)
059: throws InvalidConfigurationException {
060: super (gbeanInstance, referenceInfo, kernel,
061: hasTargets(referencePatterns));
062: listener = createLifecycleListener();
063: if (referencePatterns != null) {
064: setReferencePatterns(referencePatterns);
065: }
066: }
067:
068: private static boolean hasTargets(
069: ReferencePatterns referencePatterns) {
070: if (referencePatterns == null) {
071: return false;
072: }
073: if (referencePatterns.isResolved()) {
074: return true;
075: }
076: return !referencePatterns.getPatterns().isEmpty();
077: }
078:
079: public synchronized boolean start() {
080: // We only need to start if there are patterns and we don't already have a proxy
081: if (!patterns.isEmpty() && getProxy() == null) {
082: // add a dependency on our target and create the proxy
083: setProxy(new ProxyCollection(getName(), getReferenceType(),
084: getTargets(), getKernel()));
085: }
086: return true;
087: }
088:
089: public synchronized void stop() {
090: ProxyCollection proxy = (ProxyCollection) getProxy();
091: if (proxy != null) {
092: proxy.destroy();
093: setProxy(null);
094: }
095: }
096:
097: protected synchronized void targetAdded(AbstractName target) {
098: ProxyCollection proxy = (ProxyCollection) getProxy();
099: if (proxy != null) {
100: proxy.addTarget(target);
101: }
102: }
103:
104: protected synchronized void targetRemoved(AbstractName target) {
105: ProxyCollection proxy = (ProxyCollection) getProxy();
106: if (proxy != null) {
107: proxy.removeTarget(target);
108: }
109: }
110:
111: protected LifecycleListener createLifecycleListener() {
112: return new LifecycleAdapter() {
113: public void running(AbstractName abstractName) {
114: addTarget(abstractName);
115: }
116:
117: public void stopping(AbstractName abstractName) {
118: removeTarget(abstractName);
119: }
120:
121: public void stopped(AbstractName abstractName) {
122: removeTarget(abstractName);
123: }
124:
125: public void failed(AbstractName abstractName) {
126: removeTarget(abstractName);
127: }
128:
129: public void unloaded(AbstractName abstractName) {
130: removeTarget(abstractName);
131: }
132: };
133: }
134:
135: public final synchronized Set getPatterns() {
136: return patterns;
137: }
138:
139: public final synchronized void setReferencePatterns(
140: ReferencePatterns referencePatterns) {
141: if (isOnline) {
142: throw new IllegalStateException(
143: "Pattern set can not be modified while online");
144: }
145: if (referencePatterns.isResolved()) {
146: this .patterns = Collections.unmodifiableSet(Collections
147: .singleton(new AbstractNameQuery(referencePatterns
148: .getAbstractName())));
149: } else {
150: this .patterns = Collections
151: .unmodifiableSet(referencePatterns.getPatterns());
152: }
153: }
154:
155: public final synchronized void online() {
156: Set gbeans = getKernel().listGBeans(patterns);
157: for (Iterator objectNameIterator = gbeans.iterator(); objectNameIterator
158: .hasNext();) {
159: AbstractName target = (AbstractName) objectNameIterator
160: .next();
161: if (!targets.contains(target)) {
162:
163: // if the bean is running add it to the runningTargets list
164: if (isRunning(getKernel(), target)) {
165: targets.add(target);
166: }
167: }
168: }
169:
170: getKernel().getLifecycleMonitor().addLifecycleListener(
171: listener, patterns);
172: isOnline = true;
173: }
174:
175: public final synchronized void offline() {
176: // make sure we are stoped
177: stop();
178:
179: getKernel().getLifecycleMonitor().removeLifecycleListener(
180: listener);
181:
182: targets.clear();
183: isOnline = false;
184: }
185:
186: protected final Set getTargets() {
187: return targets;
188: }
189:
190: protected final void addTarget(AbstractName abstractName) {
191: if (!targets.contains(abstractName)) {
192: targets.add(abstractName);
193: targetAdded(abstractName);
194: }
195: }
196:
197: protected final void removeTarget(AbstractName abstractName) {
198: boolean wasTarget = targets.remove(abstractName);
199: if (wasTarget) {
200: targetRemoved(abstractName);
201: }
202: }
203:
204: }
|