001: /*
002: * JBoss, Home of Professional Open Source.
003: * Copyright 2006, Red Hat Middleware LLC, and individual contributors
004: * as indicated by the @author tags. See the copyright.txt file in the
005: * distribution for a full listing of individual contributors.
006: *
007: * This is free software; you can redistribute it and/or modify it
008: * under the terms of the GNU Lesser General Public License as
009: * published by the Free Software Foundation; either version 2.1 of
010: * the License, or (at your option) any later version.
011: *
012: * This software is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * Lesser General Public License for more details.
016: *
017: * You should have received a copy of the GNU Lesser General Public
018: * License along with this software; if not, write to the Free
019: * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
021: */
022: package org.jboss.test.testbeancluster.test;
023:
024: import java.util.Date;
025: import java.util.Properties;
026:
027: import javax.management.ObjectName;
028: import javax.naming.Context;
029: import javax.naming.InitialContext;
030:
031: import junit.framework.Test;
032:
033: import org.jboss.jmx.adaptor.rmi.RMIAdaptor;
034: import org.jboss.test.testbeancluster.interfaces.StatefulSession;
035: import org.jboss.test.testbean.interfaces.StatefulSessionHome;
036:
037: import org.jboss.test.JBossClusteredTestCase;
038: import org.jboss.test.testbeancluster.interfaces.NodeAnswer;
039:
040: /**
041: * Test passivation and expiration of clustered SLSBs.
042: *
043: * @author <a href="mailto:sacha.labourey@cogito-info.ch">Sacha Labourey</a>.
044: * @author Scott.Stark@jboss.org
045: * @author Brian Stansberry
046: *
047: * @version $Revision: 56924 $
048: */
049: public class StatefulPassivationExpirationUnitTestCase extends
050: JBossClusteredTestCase {
051: static boolean deployed = false;
052: public static int test = 0;
053: static Date startDate = new Date();
054:
055: protected final String namingFactory = System
056: .getProperty(Context.INITIAL_CONTEXT_FACTORY);
057:
058: protected final String providerURL = System
059: .getProperty(Context.PROVIDER_URL);
060:
061: public StatefulPassivationExpirationUnitTestCase(String name) {
062: super (name);
063: }
064:
065: public static Test suite() throws Exception {
066: Test t1 = JBossClusteredTestCase.getDeploySetup(
067: StatefulPassivationExpirationUnitTestCase.class,
068: "testbeancluster.jar");
069: return t1;
070: }
071:
072: /**
073: * The test creates 500 stateful session beans, executes some calls to
074: * stress state replication, waits for passivation and exipration to kick
075: * in, and then updates the sessions to produce the session removal
076: * conflict seen in JBAS-1560. This is sensative to timing issues so a
077: * failure in activation can show up; we catch any NoSuchObjectExceptio
078: * to handle this.
079: *
080: * @throws Exception
081: */
082: public void testStatefulPassivationExpiration() throws Exception {
083: log.info("+++ testStatefulPassivationExpiration");
084:
085: // Connect to the server0 JNDI
086: String[] urls = getNamingURLs();
087: Properties env1 = new Properties();
088: env1.setProperty(Context.INITIAL_CONTEXT_FACTORY,
089: "org.jnp.interfaces.NamingContextFactory");
090: env1.setProperty(Context.PROVIDER_URL, urls[0]);
091: InitialContext ctx = new InitialContext(env1);
092:
093: int beanCount = 500;
094: StatefulSessionHome home = (StatefulSessionHome) ctx
095: .lookup("nextgen_ExpiredStatefulSession");
096: long start = System.currentTimeMillis();
097: log.info("Start bean creation");
098: StatefulSession[] beans = new StatefulSession[beanCount];
099: long[] accessStamp = new long[beanCount];
100: for (int n = 0; n < beans.length; n++) {
101: beans[n] = (StatefulSession) home
102: .create("testStatefulPassivationExpiration#" + n);
103: accessStamp[n] = System.currentTimeMillis();
104: }
105: long end = System.currentTimeMillis();
106: log.info("End bean creation, elapsed=" + (end - start));
107:
108: int N = 5000;
109: long min = 99999, max = 0, maxInactive = 0;
110: for (int n = 0; n < N; n++) {
111: int id = n % beans.length;
112: StatefulSession bean = beans[id];
113: if (bean == null)
114: continue; // bean timed out and removed
115: String name = "testStatefulPassiviationExpiration#" + id;
116: long callStart = System.currentTimeMillis();
117: long inactive = callStart - accessStamp[id];
118: try {
119: bean.setName(name);
120: NodeAnswer node = bean.getNodeState();
121: long now = System.currentTimeMillis();
122: long elapsed = now - callStart;
123: accessStamp[id] = now;
124: assertTrue("NodeAnswer == " + name, node.answer
125: .equals(name));
126: min = Math.min(min, elapsed);
127: max = Math.max(max, elapsed);
128: maxInactive = Math.max(maxInactive, inactive);
129: log.debug(n + ", elapsed=" + elapsed + ", inactive="
130: + inactive);
131: } catch (java.rmi.NoSuchObjectException nso) {
132: log.debug(n + " Caught NoSuchObjectException on bean "
133: + id + " -- inactive time = " + inactive);
134: // Remove the bean as it will never succeed again
135: beans[id] = null;
136: }
137: }
138: log.info(N + " calls complete, max=" + max + ", min=" + min
139: + ", maxInactive=" + maxInactive);
140:
141: Thread.sleep(15000);
142: start = System.currentTimeMillis();
143: for (int n = 0; n < beans.length; n++) {
144: beans[n] = (StatefulSession) home
145: .create("testStatefulPassivationExpiration#" + n);
146: accessStamp[n] = System.currentTimeMillis();
147: }
148: end = System.currentTimeMillis();
149: log.info("End second round bean creation, elapsed="
150: + (end - start));
151: for (int n = 0; n < N; n++) {
152: int id = n % beans.length;
153: StatefulSession bean = beans[id];
154: if (bean == null)
155: continue; // bean timed out and removed
156: String name = "testStatefulPassiviationExpiration#" + id;
157: long callStart = System.currentTimeMillis();
158: long inactive = callStart - accessStamp[id];
159: try {
160: bean.setName(name);
161: NodeAnswer node = bean.getNodeState();
162: long now = System.currentTimeMillis();
163: long elapsed = now - callStart;
164: accessStamp[id] = now;
165: assertTrue("NodeAnswer == " + name, node.answer
166: .equals(name));
167: min = Math.min(min, elapsed);
168: max = Math.max(max, elapsed);
169: maxInactive = Math.max(maxInactive, inactive);
170: log.debug(n + ", elapsed=" + elapsed + ", inactive="
171: + inactive);
172: } catch (java.rmi.NoSuchObjectException nso) {
173: log.debug(n + " Caught NoSuchObjectException on bean "
174: + id + " -- inactive time = "
175: + (callStart - accessStamp[id]));
176: // Remove the bean as it will never succeed again
177: beans[id] = null;
178: }
179: }
180: log.info(N + " calls complete, max=" + max + ", min=" + min
181: + ", maxInactive=" + maxInactive);
182: // BES -- max call time check removed, as it can randomly fail if there is a long GC pause
183: // assertTrue("max < 3000", max < 3000 );
184:
185: for (int n = 0; n < beans.length; n++) {
186: try {
187: if (beans[n] != null)
188: beans[n].remove();
189: } catch (java.rmi.NoSuchObjectException nso) {
190: log.debug("Caught NoSuchObjectException removing bean "
191: + n);
192: }
193: }
194:
195: // Confirm that the bean cache is empty
196: String oNameS = "jboss.j2ee:jndiName=ExpiredStatefulSession,plugin=cache,service=EJB";
197: ObjectName oName = new ObjectName(oNameS);
198: RMIAdaptor[] adaptors = getAdaptors();
199: Long cacheCount = (Long) adaptors[0].getAttribute(oName,
200: "CacheSize");
201: assertEquals("CacheSize is zero", 0, cacheCount.longValue());
202: // Checking the passivated count is invalid, as it doesn't get reduced
203: // when remove() is called on a bean -- only when the passivation cleanup
204: // thread runs
205: //cacheCount = (Long) adaptors[0].getAttribute(oName, "PassivatedCount");
206: //assertEquals("PassivatedCount is zero", 0, cacheCount.longValue());
207: }
208: }
|