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.jetty6;
017:
018: import java.io.IOException;
019: import java.util.Map;
020: import java.util.Set;
021:
022: import javax.security.auth.Subject;
023: import javax.security.jacc.PolicyContext;
024: import javax.servlet.ServletContext;
025: import javax.servlet.ServletException;
026: import javax.servlet.ServletRequest;
027: import javax.servlet.ServletResponse;
028: import javax.servlet.UnavailableException;
029: import javax.servlet.http.HttpServletRequest;
030:
031: import org.apache.geronimo.gbean.GBeanInfo;
032: import org.apache.geronimo.gbean.GBeanInfoBuilder;
033: import org.apache.geronimo.gbean.GBeanLifecycle;
034: import org.apache.geronimo.j2ee.j2eeobjectnames.NameFactory;
035: import org.apache.geronimo.webservices.POJOWebServiceServlet;
036: import org.apache.geronimo.webservices.WebServiceContainer;
037: import org.apache.geronimo.webservices.WebServiceContainerInvoker;
038: import org.apache.geronimo.webservices.WebServiceContainerFactory;
039: import org.mortbay.jetty.Request;
040: import org.mortbay.jetty.servlet.ServletHolder;
041:
042: /**
043: * This is intended to hold the web service stack for an axis POJO web service.
044: * It is starting life as a copy of JettyServletHolder.
045: *
046: * @version $Rev: 609448 $ $Date: 2008-01-06 14:31:09 -0800 (Sun, 06 Jan 2008) $
047: */
048: public class JettyPOJOWebServiceHolder implements ServletNameSource,
049: GBeanLifecycle {
050: private final ServletHolder servletHolder;
051: private final WebServiceContainer webServiceContainer;
052: private final Set servletMappings;
053: private final JettyServletRegistration context;
054: private final String pojoClassName;
055:
056: //todo consider interface instead of this constructor for endpoint use.
057: public JettyPOJOWebServiceHolder() {
058: servletHolder = null;
059: webServiceContainer = null;
060: servletMappings = null;
061: context = null;
062: pojoClassName = null;
063: }
064:
065: public JettyPOJOWebServiceHolder(String pojoClassName,
066: String servletName, Map initParams, Integer loadOnStartup,
067: Set servletMappings, String runAsRole,
068: WebServiceContainerFactory webServiceContainerFactory,
069: JettyServletRegistration context) throws Exception {
070: Subject runAsSubject = context == null ? null : context
071: .getSubjectForRole(runAsRole);
072: servletHolder = new InternalJettyServletHolder(
073: context == null ? null : context.getLifecycleChain(),
074: runAsSubject, context);
075: //context will be null only for use as "default servlet info holder" in deployer.
076:
077: this .pojoClassName = pojoClassName;
078: this .context = context;
079: this .webServiceContainer = webServiceContainerFactory == null ? null
080: : webServiceContainerFactory.getWebServiceContainer();
081: this .servletMappings = servletMappings;
082: if (context != null) {
083: servletHolder.setName(servletName);
084: servletHolder.setClassName(POJOWebServiceServlet.class
085: .getName());
086: servletHolder.setInitParameters(initParams);
087: if (loadOnStartup != null) {
088: servletHolder.setInitOrder(loadOnStartup.intValue());
089: }
090: }
091: }
092:
093: //todo how do we stop/destroy the servlet?
094: //todo is start called twice???
095:
096: public String getServletName() {
097: return servletHolder.getName();
098: }
099:
100: /**
101: * TODO THIS IS NOT CALLED!!! only the ServletHolder is!!
102: * Service a request with this servlet. Set the ThreadLocal to hold the
103: * current JettyServletHolder.
104: */
105: public void handle(ServletRequest request, ServletResponse response)
106: throws ServletException, UnavailableException, IOException {
107:
108: // TODO There has to be some way to get this in on the Servlet's init method.
109: // request.setAttribute(POJOWebServiceServlet.WEBSERVICE_CONTAINER, webServiceContainer);
110:
111: InternalJettyServletHolder
112: .setCurrentServletName(getServletName());
113: PolicyContext.setHandlerData(Request
114: .getRequest((HttpServletRequest) request));
115:
116: servletHolder.handle(request, response);
117: }
118:
119: public void doStart() throws Exception {
120: if (context != null) {
121: Class pojoClass = context.getWebClassLoader().loadClass(
122: pojoClassName);
123:
124: /* DMB: Hack! I really just want to override initServlet and give a reference of the WebServiceContainer to the servlet before we call init on it.
125: * But this will have to do instead....
126: */
127: ServletContext servletContext = this .context
128: .getServletHandler().getServletContext();
129:
130: // Make up an ID for the WebServiceContainer
131: // put a reference the ID in the init-params
132: // put the WebServiceContainer in the webapp context keyed by its ID
133: String webServicecontainerID = getServletName()
134: + WebServiceContainerInvoker.WEBSERVICE_CONTAINER
135: + webServiceContainer.hashCode();
136: servletHolder.setInitParameter(
137: WebServiceContainerInvoker.WEBSERVICE_CONTAINER,
138: webServicecontainerID);
139: servletContext.setAttribute(webServicecontainerID,
140: webServiceContainer);
141:
142: // Same for the POJO Class
143: String pojoClassID = getServletName()
144: + POJOWebServiceServlet.POJO_CLASS
145: + pojoClass.hashCode();
146: servletHolder.setInitParameter(
147: POJOWebServiceServlet.POJO_CLASS, pojoClassID);
148: servletContext.setAttribute(pojoClassID, pojoClass);
149:
150: //this now starts the servlet in the appropriate context
151: //TODO check that we should not call this a servlet for jsr-77 benefit.
152: context.registerServletHolder(servletHolder,
153: getServletName(), this .servletMappings, null);
154: servletHolder.start();
155: }
156: }
157:
158: public void doStop() throws Exception {
159: servletHolder.stop();
160: }
161:
162: public void doFail() {
163: try {
164: servletHolder.stop();
165: } catch (Exception e) {
166: //ignore ??
167: }
168: }
169:
170: public static final GBeanInfo GBEAN_INFO;
171:
172: static {
173: GBeanInfoBuilder infoBuilder = GBeanInfoBuilder.createStatic(
174: JettyPOJOWebServiceHolder.class,
175: NameFactory.SERVLET_WEB_SERVICE_TEMPLATE);
176: //todo replace with interface
177: // infoBuilder.addInterface(ServletHolder.class);
178:
179: infoBuilder.addAttribute("pojoClassName", String.class, true);
180: infoBuilder.addAttribute("servletName", String.class, true);
181: infoBuilder.addAttribute("initParams", Map.class, true);
182: infoBuilder.addAttribute("loadOnStartup", Integer.class, true);
183: infoBuilder.addAttribute("servletMappings", Set.class, true);
184: infoBuilder.addAttribute("runAsRole", String.class, true);
185: infoBuilder.addReference("WebServiceContainerFactory",
186: WebServiceContainerFactory.class);
187: infoBuilder.addReference("JettyServletRegistration",
188: JettyServletRegistration.class);
189:
190: infoBuilder.setConstructor(new String[] { "pojoClassName",
191: "servletName", "initParams", "loadOnStartup",
192: "servletMappings", "runAsRole",
193: "WebServiceContainerFactory",
194: "JettyServletRegistration" });
195:
196: GBEAN_INFO = infoBuilder.getBeanInfo();
197: }
198:
199: public static GBeanInfo getGBeanInfo() {
200: return GBEAN_INFO;
201: }
202:
203: }
|