1 /**
2 *
3 * Copyright 2003-2004 The Apache Software Foundation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18 package org.apache.geronimo.gbean.runtime;
19
20 import org.apache.geronimo.gbean.AbstractName;
21 import org.apache.geronimo.gbean.GReferenceInfo;
22 import org.apache.geronimo.gbean.InvalidConfigurationException;
23 import org.apache.geronimo.gbean.ReferencePatterns;
24 import org.apache.geronimo.gbean.AbstractNameQuery;
25 import org.apache.geronimo.kernel.Kernel;
26 import org.apache.geronimo.kernel.lifecycle.LifecycleAdapter;
27 import org.apache.geronimo.kernel.lifecycle.LifecycleListener;
28
29 import java.util.Collections;
30 import java.util.HashSet;
31 import java.util.Iterator;
32 import java.util.Set;
33
34 /**
35 * @version $Rev:386515 $ $Date: 2006-03-18 16:52:38 -0800 (Sat, 18 Mar 2006) $
36 */
37 public class GBeanCollectionReference extends AbstractGBeanReference {
38 /**
39 * is this reference online
40 */
41 private boolean isOnline = false;
42
43 /**
44 * The target objectName patterns to watch for a connection.
45 */
46 private Set patterns = Collections.EMPTY_SET;
47
48 /**
49 * Current set of targets
50 */
51 private final Set targets = new HashSet();
52
53 /**
54 * Our listener for lifecycle events
55 */
56 private final LifecycleListener listener;
57
58 public GBeanCollectionReference(GBeanInstance gbeanInstance, GReferenceInfo referenceInfo, Kernel kernel, ReferencePatterns referencePatterns) throws InvalidConfigurationException {
59 super(gbeanInstance, referenceInfo, kernel, hasTargets(referencePatterns));
60 listener = createLifecycleListener();
61 if (referencePatterns != null) {
62 setReferencePatterns(referencePatterns);
63 }
64 }
65
66 private static boolean hasTargets(ReferencePatterns referencePatterns) {
67 if (referencePatterns == null) {
68 return false;
69 }
70 if (referencePatterns.isResolved()) {
71 return true;
72 }
73 return !referencePatterns.getPatterns().isEmpty();
74 }
75
76 public synchronized boolean start() {
77
78 if (!patterns.isEmpty() && getProxy() == null) {
79
80 setProxy(new ProxyCollection(getName(), getReferenceType(), getTargets(), getKernel()));
81 }
82 return true;
83 }
84
85 public synchronized void stop() {
86 ProxyCollection proxy = (ProxyCollection) getProxy();
87 if (proxy != null) {
88 proxy.destroy();
89 setProxy(null);
90 }
91 }
92
93 protected synchronized void targetAdded(AbstractName target) {
94 ProxyCollection proxy = (ProxyCollection) getProxy();
95 if (proxy != null) {
96 proxy.addTarget(target);
97 }
98 }
99
100 protected synchronized void targetRemoved(AbstractName target) {
101 ProxyCollection proxy = (ProxyCollection) getProxy();
102 if (proxy != null) {
103 proxy.removeTarget(target);
104 }
105 }
106
107 protected LifecycleListener createLifecycleListener() {
108 return new LifecycleAdapter() {
109 public void running(AbstractName abstractName) {
110 addTarget(abstractName);
111 }
112
113 public void stopping(AbstractName abstractName) {
114 removeTarget(abstractName);
115 }
116
117 public void stopped(AbstractName abstractName) {
118 removeTarget(abstractName);
119 }
120
121 public void failed(AbstractName abstractName) {
122 removeTarget(abstractName);
123 }
124
125 public void unloaded(AbstractName abstractName) {
126 removeTarget(abstractName);
127 }
128 };
129 }
130
131 public final synchronized Set getPatterns() {
132 return patterns;
133 }
134
135 public final synchronized void setReferencePatterns(ReferencePatterns referencePatterns) {
136 if (isOnline) {
137 throw new IllegalStateException("Pattern set can not be modified while online");
138 }
139 if (referencePatterns.isResolved()) {
140 this.patterns = Collections.unmodifiableSet(Collections.singleton(new AbstractNameQuery(referencePatterns.getAbstractName())));
141 } else {
142 this.patterns = Collections.unmodifiableSet(referencePatterns.getPatterns());
143 }
144 }
145
146 public final synchronized void online() {
147 Set gbeans = getKernel().listGBeans(patterns);
148 for (Iterator objectNameIterator = gbeans.iterator(); objectNameIterator.hasNext();) {
149 AbstractName target = (AbstractName) objectNameIterator.next();
150 if (!targets.contains(target)) {
151
152
153 if (isRunning(getKernel(), target)) {
154 targets.add(target);
155 }
156 }
157 }
158
159 getKernel().getLifecycleMonitor().addLifecycleListener(listener, patterns);
160 isOnline = true;
161 }
162
163 public final synchronized void offline() {
164
165 stop();
166
167 getKernel().getLifecycleMonitor().removeLifecycleListener(listener);
168
169 targets.clear();
170 isOnline = false;
171 }
172
173 protected final Set getTargets() {
174 return targets;
175 }
176
177 protected final void addTarget(AbstractName abstractName) {
178 if (!targets.contains(abstractName)) {
179 targets.add(abstractName);
180 targetAdded(abstractName);
181 }
182 }
183
184 protected final void removeTarget(AbstractName abstractName) {
185 boolean wasTarget = targets.remove(abstractName);
186 if (wasTarget) {
187 targetRemoved(abstractName);
188 }
189 }
190
191 }