/* * The contents of this file are subject to the terms * of the Common Development and Distribution License * (the License). You may not use this file except in * compliance with the License. * * You can obtain a copy of the license at * https://glassfish.dev.java.net/public/CDDLv1.0.html or * glassfish/bootstrap/legal/CDDLv1.0.txt. * See the License for the specific language governing * permissions and limitations under the License. * * When distributing Covered Code, include this CDDL * Header Notice in each file and include the License file * at glassfish/bootstrap/legal/CDDLv1.0.txt. * If applicable, add the following below the CDDL Header, * with the fields enclosed by brackets [] replaced by * you own identifying information: * "Portions Copyrighted [year] [name of copyright owner]" * * Copyright 2006 Sun Microsystems, Inc. All rights reserved. */ package com.sun.appserv.server; import java.util.HashSet; import java.util.Set; import java.util.List; import java.util.ArrayList; import java.util.Iterator; import com.sun.enterprise.deployment.WebBundleDescriptor; import com.sun.enterprise.deployment.Application; import com.sun.web.security.RealmAdapter; import org.apache.catalina.Context; import org.apache.catalina.core.StandardContext; import com.sun.enterprise.config.ConfigContext; import com.sun.enterprise.config.ConfigException; import com.sun.enterprise.config.serverbeans.ServerBeansFactory; import com.sun.enterprise.config.serverbeans.Server; import com.sun.enterprise.config.serverbeans.Applications; import com.sun.enterprise.config.serverbeans.ApplicationRef; import com.sun.enterprise.config.serverbeans.LifecycleModule; import com.sun.enterprise.config.serverbeans.ElementProperty; import com.sun.enterprise.server.ServerContext; import com.sun.appserv.management.util.misc.TimingDelta; import com.sun.appserv.management.util.misc.RunnableBase; import com.sun.appserv.management.helper.AMXDebugHelper; /** * Support class to assist in firing LifecycleEvent notifications to * registered LifecycleListeners. * * @author Sridatta Viswanath * @version $Id: LifecycleModuleService.java,v 1.7 2006/12/01 09:55:32 binod Exp $ */ public class LifecycleModuleService implements ServerLifecycle { private OneTimeIniter mOneTimeIniter; private final AMXDebugHelper mDebug = new AMXDebugHelper( "LifecycleModuleService" ); private void debug( final Object...args ) { mDebug.println( args ); } /** * The set of registered LifecycleListeners for event notifications. */ private final List listeners = new ArrayList(); private final class OneTimeIniter extends RunnableBase { private final ServerContext mServerContext; public OneTimeIniter( final ServerContext serverContext ) { mServerContext = serverContext; } protected void doRun() throws ConfigException, ServerLifecycleException { //ROB: config changes //Applications apps = //ServerBeansFactory.getServerBean(mServerContext.getConfigContext()).getApplications(); final Applications apps = ServerBeansFactory.getApplicationsBean(mServerContext.getConfigContext()); if (apps == null) return; final LifecycleModule[] lcms = apps.getLifecycleModule(); if(lcms == null) return; final HashSet listenerSet = new HashSet(); for(int i=0;i order) { break; } } this.listeners.add(i,next); } } private void initialize( final ServerContext context) throws ServerLifecycleException { if (listeners.isEmpty()) return; final ClassLoader cl = Thread.currentThread().getContextClassLoader(); for( final ServerLifecycleModule next : listeners ) { next.onInitialization(context); } // set it back resetClassLoader(cl); } public LifecycleModuleService() { } public synchronized void onInitialization( final ServerContext context) throws ServerLifecycleException { mOneTimeIniter = new OneTimeIniter( context ); mOneTimeIniter.submit( RunnableBase.SUBMIT_ASYNC ); // leave it running; we'll sync up with it in start() } /** * Returns true if life cycle module is enabled in the application * level and in the application ref level. * * @param lcm life cycle module * @param config config context * * @return true if life cycle module is enabled */ private boolean isEnabled(LifecycleModule lcm, ConfigContext config) { try { // return false if arguments are null if (lcm == null || config == null) { return false; } // find the ref to the life cycle module final Server server = ServerBeansFactory.getServerBean(config); final ApplicationRef appRef=server.getApplicationRefByRef(lcm.getName()); // true if enabled in both lifecyle module and in the ref return ((lcm.isEnabled()) && (appRef != null && appRef.isEnabled())); } catch (ConfigException e) { return false; } } private void resetClassLoader(final ClassLoader c) { // set the common class loader as the thread context class loader java.security.AccessController.doPrivileged( new java.security.PrivilegedAction() { public Object run() { Thread.currentThread().setContextClassLoader(c); return null; } } ); } public void onStartup(ServerContext context) throws ServerLifecycleException { final TimingDelta delta = new TimingDelta(); // wait for initialization to finish mOneTimeIniter.waitDoneThrow(); debug( "Millis for initer to run: ", (mOneTimeIniter.getNanosFromSubmit() / (1000*1000)), ", wait time = ", delta.elapsedMillis() ); mOneTimeIniter = null; if (listeners.isEmpty()) return; final ClassLoader cl = Thread.currentThread().getContextClassLoader(); for( final ServerLifecycleModule next : listeners ) { // the SERVLET invocation context so J2EE invocations from // lifecycle modules get a legal ComponentInvocation. // create an invocation context that is of the type // SERVLET_INVOCATION Context invocationContext = new StandardContext(); WebBundleDescriptor wbd = new WebBundleDescriptor(); Application.createApplication(next.getName(), wbd.getModuleDescriptor()); invocationContext.setRealm(new RealmAdapter(wbd, false)); next.onStartup(context, invocationContext); } // set it back resetClassLoader(cl); } public void onReady(ServerContext context) throws ServerLifecycleException { if (listeners.isEmpty()) return; final ClassLoader cl = Thread.currentThread().getContextClassLoader(); for( final ServerLifecycleModule next : listeners ) { next.onReady(context); } // set it back resetClassLoader(cl); } public void onShutdown() throws ServerLifecycleException { if (listeners.isEmpty()) return; final ClassLoader cl = Thread.currentThread().getContextClassLoader(); for( final ServerLifecycleModule next : listeners ) { next.onShutdown(); } // set it back resetClassLoader(cl); } public void onTermination() throws ServerLifecycleException { if (listeners.isEmpty()) return; final ClassLoader cl = Thread.currentThread().getContextClassLoader(); for( final ServerLifecycleModule next : listeners ) { next.onTermination(); } // set it back resetClassLoader(cl); } }