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: *
017: * $Header:$
018: */
019: package org.apache.beehive.controls.system.ejb;
020:
021: import java.io.File;
022: import java.io.FileInputStream;
023: import java.io.FileNotFoundException;
024: import java.io.FileOutputStream;
025: import java.io.IOException;
026: import javax.xml.parsers.DocumentBuilder;
027: import javax.xml.parsers.DocumentBuilderFactory;
028: import javax.xml.parsers.ParserConfigurationException;
029: import javax.xml.transform.Transformer;
030: import javax.xml.transform.TransformerConfigurationException;
031: import javax.xml.transform.TransformerException;
032: import javax.xml.transform.TransformerFactory;
033: import javax.xml.transform.OutputKeys;
034: import javax.xml.transform.dom.DOMSource;
035: import javax.xml.transform.stream.StreamResult;
036:
037: import org.apache.beehive.controls.api.assembly.ControlAssembler;
038: import org.apache.beehive.controls.api.assembly.ControlAssemblyContext;
039: import org.apache.beehive.controls.api.assembly.ControlAssemblyException;
040: import org.apache.beehive.controls.system.ejb.internal.EJBJarDescriptorHandler;
041: import org.apache.beehive.controls.system.ejb.internal.WebDescriptorHandler;
042: import org.w3c.dom.Document;
043: import org.w3c.dom.DocumentType;
044: import org.xml.sax.SAXException;
045:
046: /**
047: * The EJBControl needs to inject EJB reference entries into the
048: * DD of its containing module for cases where ejb-link is used.
049: */
050: public class EJBControlAssembler implements ControlAssembler {
051: public void assemble(ControlAssemblyContext cac)
052: throws ControlAssemblyException {
053: cac.getMessager().printNotice(
054: "EJBControlAssembler.assemble() called");
055:
056: Class controlInterface = cac.getControlType();
057: EJBInfo ei = new EJBInfo(controlInterface);
058:
059: EJBControl.EJBHome ea = cac
060: .getControlAnnotation(EJBControl.EJBHome.class);
061: if (ea == null) {
062: cac.getMessager().printError(
063: "Missing EJBHome annotation on control?!");
064: return;
065: }
066:
067: String ejbLinkValue = ea.ejbLink();
068: if (ejbLinkValue == null || ejbLinkValue.length() == 0)
069: // Not using ejb-link, so no ejb-ref injection needed
070: return;
071:
072: if (cac instanceof ControlAssemblyContext.EJBModule)
073: // insert any required <ejb-ref> entries into the deployment descriptor
074: updateEJBJar((ControlAssemblyContext.EJBModule) cac, ei,
075: ejbLinkValue);
076: else if (cac instanceof ControlAssemblyContext.WebAppModule)
077: updateWebApp((ControlAssemblyContext.WebAppModule) cac, ei,
078: ejbLinkValue);
079: else
080: cac
081: .getMessager()
082: .printNotice(
083: "EJBControlAssembler - no work to do, assembly context is not EJB.");
084: }
085:
086: protected void updateEJBJar(
087: ControlAssemblyContext.EJBModule ejbAssemblyContext,
088: EJBInfo ejbInfo, String ejbLinkValue)
089: throws ControlAssemblyException {
090: ControlAssemblyContext cac = (ControlAssemblyContext) ejbAssemblyContext;
091:
092: cac.getMessager().printNotice(
093: "EJBControlAssembler.updateEJBJar() called");
094: cac.getMessager().printNotice(" ejbInfo=" + ejbInfo);
095: cac.getMessager().printNotice(" ejbLinkValue=" + ejbLinkValue);
096:
097: File ejbJarFile = ejbAssemblyContext.getEjbJarXml();
098: FileInputStream ejbJarStream;
099: try {
100: ejbJarStream = new FileInputStream(ejbJarFile);
101: } catch (FileNotFoundException fnfe) {
102: String msg = "EJBControlAssembler aborted: "
103: + "caught FileNotFoundException attempting to read file "
104: + ejbJarFile.getAbsolutePath() + ". Message: "
105: + fnfe.getMessage();
106: cac.getMessager().printWarning(msg);
107: return;
108: }
109:
110: try {
111: // get the existing <ejb-jar> XBean from the stream
112: DocumentBuilderFactory dbf = DocumentBuilderFactory
113: .newInstance();
114: dbf.setValidating(false);
115: DocumentBuilder db = dbf.newDocumentBuilder();
116: Document ejbDoc = db.parse(ejbJarStream);
117:
118: ejbJarStream.close();
119: ejbJarStream = null;
120:
121: EJBJarDescriptorHandler ejbHandler = EJBJarDescriptorHandler
122: .getInstance();
123: ejbHandler.assemble(ejbDoc, ejbInfo, ejbLinkValue);
124:
125: // overwrite existing ejb-jar.xml file with new document
126: writeXML(cac, ejbDoc, ejbJarFile);
127: } catch (IOException ioe) {
128: String msg = "EJBControlAssembler: caught IOException "
129: + "attempting to write to file "
130: + ejbJarFile.getAbsolutePath() + ". Message: "
131: + ioe.getMessage();
132: cac.getMessager().printError(msg);
133: } catch (ParserConfigurationException e) {
134: String msg = "EJBControlAssembler: caught ParserConfigurationException "
135: + "attempting to read to file "
136: + ejbJarFile.getAbsolutePath()
137: + ". Message: "
138: + e.getMessage();
139: cac.getMessager().printError(msg);
140: } catch (SAXException e) {
141: String msg = "EJBControlAssembler: caught SAXException "
142: + "attempting to read to file "
143: + ejbJarFile.getAbsolutePath() + ". Message: "
144: + e.getMessage();
145: cac.getMessager().printError(msg);
146: } finally {
147: try {
148: if (ejbJarStream != null)
149: ejbJarStream.close();
150: } catch (IOException e) { /* ignore */
151: }
152: }
153: }
154:
155: protected void updateWebApp(
156: ControlAssemblyContext.WebAppModule webAssemblyContext,
157: EJBInfo ejbInfo, String ejbLinkValue)
158: throws ControlAssemblyException {
159: ControlAssemblyContext cac = (ControlAssemblyContext) webAssemblyContext;
160:
161: System.err.println("EJBControlAssembler.updateWebApp() called");
162: System.err.println("ejbInfo =" + ejbInfo);
163: System.err.println("ejbLinkValue =" + ejbLinkValue);
164: File webXmlFile = webAssemblyContext.getWebXml();
165: FileInputStream webXmlStream;
166: try {
167: webXmlStream = new FileInputStream(webXmlFile);
168: } catch (FileNotFoundException fnfe) {
169: String msg = "EJBControlAssembler: "
170: + "caught FileNotFoundException attempting to read file "
171: + webXmlFile.getAbsolutePath() + ". Message: "
172: + fnfe.getMessage();
173: cac.getMessager().printError(msg);
174: return;
175: }
176:
177: try {
178: // parse the web.xml file
179: DocumentBuilderFactory dbf = DocumentBuilderFactory
180: .newInstance();
181: dbf.setValidating(false);
182: DocumentBuilder db = dbf.newDocumentBuilder();
183: Document webAppDoc = db.parse(webXmlStream);
184:
185: webXmlStream.close();
186: webXmlStream = null;
187:
188: WebDescriptorHandler webHandler = WebDescriptorHandler
189: .getInstance();
190: webHandler.assemble(webAppDoc, ejbInfo, ejbLinkValue);
191:
192: // overwrite existing web.xml file with new document
193: writeXML(cac, webAppDoc, webXmlFile);
194: } catch (IOException ioe) {
195: String msg = "EJBControlAssembler: caught IOException "
196: + "attempting to write to file "
197: + webXmlFile.getAbsolutePath() + ". Message: "
198: + ioe.getMessage();
199: cac.getMessager().printError(msg);
200: } catch (ParserConfigurationException e) {
201: String msg = "EJBControlAssembler: caught ParserConfigurationException "
202: + "attempting to read to file "
203: + webXmlFile.getAbsolutePath()
204: + ". Message: "
205: + e.getMessage();
206: cac.getMessager().printError(msg);
207: } catch (SAXException e) {
208: String msg = "EJBControlAssembler: caught SAXException "
209: + "attempting to read to file "
210: + webXmlFile.getAbsolutePath() + ". Message: "
211: + e.getMessage();
212: cac.getMessager().printError(msg);
213: } finally {
214: try {
215: if (webXmlStream != null)
216: webXmlStream.close();
217: } catch (IOException e) { /* ignore */
218: }
219: }
220:
221: }
222:
223: private void writeXML(ControlAssemblyContext cac, Document doc,
224: File outputFile) {
225:
226: TransformerFactory transformerFactory = TransformerFactory
227: .newInstance();
228: try {
229: transformerFactory.setAttribute("indent-number", 2);
230: } catch (IllegalArgumentException e) {
231: // not a fatal error, just means underlying parser implementation does not support indent-number.
232: String msg = "EJBControlAssembler: Warning -- Caught IllegalArgumentException "
233: + "attempting to set transformer factory attribute: 'indent-number'. Message: "
234: + e.getMessage();
235:
236: cac.getMessager().printNotice(msg);
237: }
238:
239: Transformer transformer;
240: FileOutputStream fos = null;
241: try {
242: transformer = transformerFactory.newTransformer();
243: try {
244: transformer.setOutputProperty(OutputKeys.INDENT, "yes");
245: DocumentType docType = doc.getDoctype();
246: if (docType != null) {
247: transformer.setOutputProperty(
248: OutputKeys.DOCTYPE_PUBLIC, docType
249: .getPublicId());
250: transformer.setOutputProperty(
251: OutputKeys.DOCTYPE_SYSTEM, docType
252: .getSystemId());
253: }
254: } catch (IllegalArgumentException e) {
255: // just keep going not a fatal error, just means underlying parser implementation
256: // does not support one of these options.
257: String msg = "EJBControlAssembler: Warning -- Caught IllegalArgumentException "
258: + "attempting to set transformer option. Message: "
259: + e.getMessage();
260:
261: cac.getMessager().printNotice(msg);
262: }
263:
264: DOMSource source = new DOMSource(doc);
265: fos = new FileOutputStream(outputFile);
266: StreamResult stream = new StreamResult(fos);
267: transformer.transform(source, stream);
268:
269: } catch (TransformerConfigurationException e) {
270: String msg = "EJBControlAssembler: caught TransformerConfigurationException "
271: + "attempting to write to file "
272: + outputFile.getAbsolutePath()
273: + ". Message: "
274: + e.getMessage();
275: cac.getMessager().printError(msg);
276: } catch (FileNotFoundException e) {
277: String msg = "EJBControlAssembler aborted: "
278: + "caught FileNotFoundException attempting to write file "
279: + outputFile.getAbsolutePath() + ". Message: "
280: + e.getMessage();
281: cac.getMessager().printError(msg);
282: } catch (TransformerException e) {
283: String msg = "EJBControlAssembler: caught TransformerException "
284: + "attempting to write to file "
285: + outputFile.getAbsolutePath()
286: + ". Message: "
287: + e.getMessage();
288: cac.getMessager().printError(msg);
289: } finally {
290: if (fos != null) {
291: try {
292: fos.close();
293: } catch (IOException e) { /* ignore */
294: }
295: }
296: }
297: }
298: }
|